All checks were successful
Deploy Indiekit Server / deploy (push) Successful in 1m15s
Posts that exist in MongoDB but not in Gitea (e.g. due to a previous failed write) caused HTTP 500 on re-publish: updateFile() tried to read the file's SHA, got 404, and threw instead of creating. Now detects Not Found and falls through to a create-style PUT (no sha field). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
96 lines
3.1 KiB
JavaScript
96 lines
3.1 KiB
JavaScript
/**
|
|
* Patch: make store-github updateFile fall back to create when the file doesn't exist.
|
|
*
|
|
* Problem: when a post was created in MongoDB but the Gitea write failed (e.g. due to a
|
|
* previous 401), IndieKit sees the post as existing and calls updateFile() on re-publish.
|
|
* updateFile() reads the file first to get its SHA, gets a 404, and throws instead of
|
|
* creating the file.
|
|
*
|
|
* Fix: if the read step returns "Not Found", proceed without a SHA. The Gitea Contents API
|
|
* (same as GitHub API) creates a new file when PUT is called without a sha field.
|
|
* Also fixes sha: false being sent (invalid) — now only sent when we actually have a SHA.
|
|
*/
|
|
|
|
import { readFile, writeFile, access } from "node:fs/promises";
|
|
|
|
const TARGET = "node_modules/@indiekit/store-github/index.js";
|
|
const MARKER = "// [patch] store-github-update-fallback";
|
|
|
|
const OLD_READ = ` let readResponse;
|
|
try {
|
|
debug(\`Try reading file \${filePath} in repo \${repo}, branch \${branch}\`);
|
|
readResponse = await this.#client(\`\${filePath}?ref=\${branch}\`);
|
|
} catch (error) {
|
|
const message = crudErrorMessage({
|
|
error,
|
|
operation: "read",
|
|
filePath,
|
|
repo,
|
|
branch,
|
|
});
|
|
debug(message);
|
|
throw new Error(message);
|
|
}
|
|
|
|
const { sha } = await readResponse.json();`;
|
|
|
|
const NEW_READ = ` let sha; ${MARKER}
|
|
try {
|
|
debug(\`Try reading file \${filePath} in repo \${repo}, branch \${branch}\`);
|
|
const readResponse = await this.#client(\`\${filePath}?ref=\${branch}\`);
|
|
const readJson = await readResponse.json();
|
|
sha = readJson.sha;
|
|
} catch (error) {
|
|
if (error.message && error.message.includes("Not Found")) {
|
|
// File doesn't exist yet — will create it via PUT without sha
|
|
debug(\`File \${filePath} not found in repo \${repo} — will create instead of update\`);
|
|
sha = undefined;
|
|
} else {
|
|
const message = crudErrorMessage({
|
|
error,
|
|
operation: "read",
|
|
filePath,
|
|
repo,
|
|
branch,
|
|
});
|
|
debug(message);
|
|
throw new Error(message);
|
|
}
|
|
}`;
|
|
|
|
const OLD_SHA = ` sha: sha || false,`;
|
|
const NEW_SHA = ` ...(sha ? { sha } : {}), ${MARKER}`;
|
|
|
|
async function exists(p) {
|
|
try { await access(p); return true; } catch { return false; }
|
|
}
|
|
|
|
if (!(await exists(TARGET))) {
|
|
console.log(`[postinstall] store-github-update-fallback: target not found, skipping`);
|
|
process.exit(0);
|
|
}
|
|
|
|
const source = await readFile(TARGET, "utf8");
|
|
|
|
if (source.includes(MARKER)) {
|
|
console.log("[postinstall] store-github-update-fallback: already patched");
|
|
process.exit(0);
|
|
}
|
|
|
|
if (!source.includes(OLD_READ)) {
|
|
console.warn("[postinstall] store-github-update-fallback: read snippet not found — skipping");
|
|
process.exit(0);
|
|
}
|
|
|
|
if (!source.includes(OLD_SHA)) {
|
|
console.warn("[postinstall] store-github-update-fallback: sha snippet not found — skipping");
|
|
process.exit(0);
|
|
}
|
|
|
|
const updated = source
|
|
.replace(OLD_READ, NEW_READ)
|
|
.replace(OLD_SHA, NEW_SHA);
|
|
|
|
await writeFile(TARGET, updated, "utf8");
|
|
console.log(`[postinstall] store-github-update-fallback: patched ${TARGET}`);
|