{"record":{"id":"3d5e9d3dc59236df","repo":"facebook/flow","slug":"failed-to-verify-shasum256-txt-against-public-key","errorCode":null,"errorMessage":"Failed to verify SHASUM256.txt against public key","messagePattern":"Failed to verify SHASUM256\\.txt against public key","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"warning","filePath":"packages/flow-for-vscode/src/utils/getVerifiedFlowBinPath.ts","lineNumber":77,"sourceCode":"\nasync function getShasums(\n  flowBinModulePath: string,\n  logger: Logger,\n): Promise<Buffer> {\n  const extensionPath = getExtensionPath();\n  try {\n    // try verifying against SHASUM256.txt.sign\n    const shasums = await readFile(\n      path.join(flowBinModulePath, 'SHASUM256.txt'),\n    );\n    const shasumsSignatureBase64 = await readFile(\n      path.join(flowBinModulePath, 'SHASUM256.txt.sign'),\n      'ascii',\n    );\n    const shasumsSignature = Buffer.from(shasumsSignatureBase64, 'base64');\n    const publicKey = await readFile(path.join(extensionPath, 'signing.pem'));\n    if (!verify('sha256', shasums, publicKey, shasumsSignature)) {\n      throw new Error('Failed to verify SHASUM256.txt against public key');\n    }\n    return shasums;\n  } catch (err: any) {\n    logger.info(`Unable to verify SHASUM256.txt.sign:\\n${err.message}`);\n    return readFile(path.join(extensionPath, 'PAST_FLOW_BIN_SHASUMS.txt'));\n  }\n}\n\nfunction getShasum(\n  shasums: string,\n  flowBinDirName: string,\n  flowBinName: string,\n): string {\n  const flowBinRelativePath = `${flowBinDirName}/${flowBinName}`;\n  // eslint-disable-next-line require-unicode-regexp\n  const shasumLines = shasums.split(/\\r?\\n/);\n  const shasumLine = shasumLines.find((line) =>\n    line.includes(flowBinRelativePath),","sourceCodeStart":59,"sourceCodeEnd":95,"githubUrl":"https://github.com/facebook/flow/blob/d1341dac899a79c027762f6b423d896045287620/packages/flow-for-vscode/src/utils/getVerifiedFlowBinPath.ts#L59-L95","documentation":"Before using a flow-bin binary, the extension verifies the package's SHASUM256.txt against the bundled public key (signing.pem) with a sha256 signature. On failure this error is thrown — but the surrounding function catches it and falls back to the historical PAST_FLOW_BIN_SHASUMS.txt, so it normally surfaces only as a log line ('Unable to verify SHASUM256.txt.sign').","triggerScenarios":"SHASUM256.txt.sign missing or corrupt, signing.pem not matching the key that signed the shipped flow-bin (extension/package version skew), or tampered checksum files. The throw is internal; the fallback path engages.","commonSituations":"Mixing a very new flow-bin with an old extension (or vice versa) across a signing-key rotation; environments stripping .sign files; older flow-bin releases predating signing.","solutions":["Usually no action — check the log line that follows; the fallback engages automatically","Align the extension and flow-bin versions so the shipped signature matches the extension's signing.pem","Update the VS Code Flow extension to obtain the current public key"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"import {access} from 'fs/promises';\nimport path from 'path';\n\nasync function signatureFilesPresent(flowBinModulePath: string): Promise<boolean> {\n  try {\n    await access(path.join(flowBinModulePath, 'SHASUM256.txt'));\n    await access(path.join(flowBinModulePath, 'SHASUM256.txt.sign'));\n    return true;\n  } catch {\n    return false;\n  }\n}","typeGuard":null,"tryCatchPattern":"// the function already catches internally and falls back to\n// PAST_FLOW_BIN_SHASUMS.txt; if you wrap it, only log:\ntry {\n  const shasums = await getShasums(flowBinModulePath, logger);\n} catch (err) {\n  logger.warn(`checksum source unavailable: ${err.message}`);\n  throw err;\n}","preventionTips":["Keep extension and flow-bin versions in sync so signing keys match","Treat repeated 'Unable to verify SHASUM256.txt.sign' log lines as a version-skew signal","Update the extension when flow rotates signing keys"],"tags":["flow-bin","signature","sha256","security","verification"],"backgroundTag":"signature-verification-failed","analyzedSha":"d1341dac899a79c027762f6b423d896045287620","analyzedAt":"2026-08-17T00:07:02.212Z","schemaVersion":2},"datasetVersion":"2026-08-17T04:17:16.089Z"}