diff --git a/src/api/core/ciphers.rs b/src/api/core/ciphers.rs
index 1948e98d..0136ca79 100644
--- a/src/api/core/ciphers.rs
+++ b/src/api/core/ciphers.rs
@@ -49,7 +49,7 @@ pub fn routes() -> Vec<Route> {
         post_cipher_admin,
         post_cipher_share,
         put_cipher_share,
-        put_cipher_share_seleted,
+        put_cipher_share_selected,
         post_cipher,
         put_cipher,
         delete_cipher_post,
@@ -212,22 +212,35 @@ pub struct Attachments2Data {
     Key: String,
 }
 
+/// Called when an org admin clones an org cipher.
 #[post("/ciphers/admin", data = "<data>")]
 fn post_ciphers_admin(data: JsonUpcase<ShareCipherData>, headers: Headers, conn: DbConn, nt: Notify) -> JsonResult {
-    let data: ShareCipherData = data.into_inner().data;
+    post_ciphers_create(data, headers, conn, nt)
+}
+
+/// Called when creating a new org-owned cipher, or cloning a cipher (whether
+/// user- or org-owned). When cloning a cipher to a user-owned cipher,
+/// `organizationId` is null.
+#[post("/ciphers/create", data = "<data>")]
+fn post_ciphers_create(data: JsonUpcase<ShareCipherData>, headers: Headers, conn: DbConn, nt: Notify) -> JsonResult {
+    let mut data: ShareCipherData = data.into_inner().data;
 
     let mut cipher = Cipher::new(data.Cipher.Type, data.Cipher.Name.clone());
     cipher.user_uuid = Some(headers.user.uuid.clone());
     cipher.save(&conn)?;
 
+    // When cloning a cipher, the Bitwarden clients seem to set this field
+    // based on the cipher being cloned (when creating a new cipher, it's set
+    // to null as expected). However, `cipher.created_at` is initialized to
+    // the current time, so the stale data check will end up failing down the
+    // line. Since this function only creates new ciphers (whether by cloning
+    // or otherwise), we can just ignore this field entirely.
+    data.Cipher.LastKnownRevisionDate = None;
+
     share_cipher_by_uuid(&cipher.uuid, data, &headers, &conn, &nt)
 }
 
-#[post("/ciphers/create", data = "<data>")]
-fn post_ciphers_create(data: JsonUpcase<ShareCipherData>, headers: Headers, conn: DbConn, nt: Notify) -> JsonResult {
-    post_ciphers_admin(data, headers, conn, nt)
-}
-
+/// Called when creating a new user-owned cipher.
 #[post("/ciphers", data = "<data>")]
 fn post_ciphers(data: JsonUpcase<CipherData>, headers: Headers, conn: DbConn, nt: Notify) -> JsonResult {
     let data: CipherData = data.into_inner().data;
@@ -407,6 +420,7 @@ fn post_ciphers_import(data: JsonUpcase<ImportData>, headers: Headers, conn: DbC
     Ok(())
 }
 
+/// Called when an org admin modifies an existing org cipher.
 #[put("/ciphers/<uuid>/admin", data = "<data>")]
 fn put_cipher_admin(
     uuid: String,
@@ -581,7 +595,7 @@ struct ShareSelectedCipherData {
 }
 
 #[put("/ciphers/share", data = "<data>")]
-fn put_cipher_share_seleted(
+fn put_cipher_share_selected(
     data: JsonUpcase<ShareSelectedCipherData>,
     headers: Headers,
     conn: DbConn,