{"record":{"id":"a7672243dba7a014","repo":"schollz/croc","slug":"invalid-stored-transfer-id","errorCode":null,"errorMessage":"Invalid stored-transfer id","messagePattern":"Invalid stored-transfer id","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"web/src/protocol/stored.ts","lineNumber":149,"sourceCode":"    parsed.hostname === \"127.0.0.1\" ||\n    parsed.hostname === \"[::1]\" ||\n    parsed.hostname === \"::1\";\n  if (\n    (parsed.protocol !== \"https:\" && !(parsed.protocol === \"http:\" && loopback)) ||\n    parsed.username ||\n    parsed.password ||\n    (parsed.pathname !== \"/\" && parsed.pathname !== \"\") ||\n    parsed.search ||\n    parsed.hash\n  ) {\n    throw new Error(\"Stored-transfer origin must contain only an HTTPS scheme and host\");\n  }\n  return parsed.origin;\n}\n\nfunction validateShare(share: StoredShare) {\n  if (!/^[A-Za-z0-9_-]{22}$/.test(share.id)) {\n    throw new Error(\"Invalid stored-transfer id\");\n  }\n  if (share.key.byteLength !== storedKeyBytes) {\n    throw new Error(\"Invalid stored-transfer key\");\n  }\n  share.origin = normalizeOrigin(share.origin);\n  return share;\n}\n\nexport function formatStoredBrowserURL(share: StoredShare) {\n  validateShare(share);\n  return `${share.origin}/s/${share.id}#v1.${base64URL(share.key)}`;\n}\n\nexport function formatStoredCLIToken(share: StoredShare) {\n  validateShare(share);\n  return [\n    storedProtocol,\n    base64URL(textEncoder.encode(share.origin)),","sourceCodeStart":131,"sourceCodeEnd":167,"githubUrl":"https://github.com/schollz/croc/blob/e25f1bdc04f07f094d50b0a1bf67e2563944b57a/web/src/protocol/stored.ts#L131-L167","documentation":"validateShare() requires the share id to be exactly 22 characters of base64url ([A-Za-z0-9_-]), which is the canonical encoding of a 16-byte server-generated id. Any other length or character (a '+' or '/' from standard base64, a truncated id, extra whitespace inside the segment) fails.","triggerScenarios":"parseStoredShare on a URL whose /s/ segment is not 22 base64url chars is caught earlier as \"Invalid stored-transfer URL\", so this fires mainly on the token branch (parts[2]) or on the client-generated share from createStoredUpload when the storage service returned a malformed id.","commonSituations":"Hand-crafted or truncated croc-store-v1 tokens; a third-party/proxy storage service that returns standard-base64 ids containing + or /; copy-paste losing characters at token segment boundaries.","solutions":["Re-copy the full share token/URL from the sender; verify the id segment is exactly 22 chars with no +, /, or = characters","If you operate the storage service, emit 16-byte ids encoded as unpadded base64url","Use isStoredShareValue()/storedShareFromLocation() for soft detection instead of letting parseStoredShare throw"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"const isValidShareId = (id: string): boolean => /^[A-Za-z0-9_-]{22}$/.test(id);","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Validate the 22-char base64url id shape before calling parseStoredShare on untrusted paste input","Prefer isStoredShareValue() for detection so malformed ids never reach the throwing path"],"tags":["validation","token","id","stored-transfer"],"backgroundTag":null,"analyzedSha":"e25f1bdc04f07f094d50b0a1bf67e2563944b57a","analyzedAt":"2026-08-15T12:53:39.096Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}