gitifact 0.8.4 → 0.8.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -0
- package/dist/browser/assets/{HgiRefresh-CAJ0Xdvi.js → HgiRefresh-BSPkIVFZ.js} +1 -1
- package/dist/browser/assets/{Markdown-ev4hMr67.js → Markdown-B1P3lpA0.js} +1 -1
- package/dist/browser/assets/Selector-BG3Gd_OR.js +2 -0
- package/dist/browser/assets/{Tab-BwJj0rUr.js → Tab-RKLZrCiK.js} +1 -1
- package/dist/browser/assets/{Table-XuC9zK9w.js → Table-DjTkmoR7.js} +2 -2
- package/dist/browser/assets/Token-CKcN25HT.css +1 -0
- package/dist/browser/assets/Token-D337a1e3.js +2 -0
- package/dist/browser/assets/{about-vlKWfG7J.js → about-D06ipt4C.js} +2 -2
- package/dist/browser/assets/activity-timeline-Bl6a55GR.js +2 -0
- package/dist/browser/assets/changelog-DCvEVceR.js +1 -0
- package/dist/browser/assets/commit-Cj7mcn9u.js +4 -0
- package/dist/browser/assets/{contributor-Bs3RWHQv.js → contributor-D1TZSDq9.js} +1 -1
- package/dist/browser/assets/contributors-lkpVuCXS.js +1 -0
- package/dist/browser/assets/{contributors._email-BR9sLgCs.js → contributors._email-B7ATmxN1.js} +1 -1
- package/dist/browser/assets/{contributors.index-FoYwG7VE.js → contributors.index-Cc0QRJwQ.js} +1 -1
- package/dist/browser/assets/dashboard.index-BNTyn3_V.js +1 -0
- package/dist/browser/assets/document-7jVYmB_Z.js +2 -0
- package/dist/browser/assets/{document-DPtVyR5y.js → document-kGFspd5u.js} +4 -4
- package/dist/browser/assets/features-CBeEOrok.js +2 -0
- package/dist/browser/assets/features-FKxsPKab.css +1 -0
- package/dist/browser/assets/{features._featureId-xxpihTEs.js → features._featureId-DGUBnzjL.js} +1 -1
- package/dist/browser/assets/{features.index-CO7APsrh.js → features.index-Dgw4kiMG.js} +1 -1
- package/dist/browser/assets/getting-started-B_LeBSZE.js +1 -0
- package/dist/browser/assets/git-DW-pzDOm.js +1 -0
- package/dist/browser/assets/index-CswY1wJ4.css +1 -0
- package/dist/browser/assets/index-IML0_BCy.js +49 -0
- package/dist/browser/assets/instructions-Qhbd8_KG.js +1 -0
- package/dist/browser/assets/{instructions._instructionId-Bp9u9xx9.js → instructions._instructionId-CnX6OyFZ.js} +1 -1
- package/dist/browser/assets/instructions.agents-0tKcPahQ.js +1 -0
- package/dist/browser/assets/instructions.index-B3v6vtEg.js +1 -0
- package/dist/browser/assets/{lazyRouteComponent-D4lq6X5s.js → lazyRouteComponent-tJOK5sxC.js} +1 -1
- package/dist/browser/assets/load-more-DVsjzCxE.js +1 -0
- package/dist/browser/assets/page-header-AS8jZ1ve.js +248 -0
- package/dist/browser/assets/records._recordId-C2qxnLKN.js +1 -0
- package/dist/browser/assets/records.commits._commit-CSa3sQ8C.js +1 -0
- package/dist/browser/assets/records.docs._docId-SIPsGTwH.js +1 -0
- package/dist/browser/assets/records.index-DoE_3GrP.js +1 -0
- package/dist/browser/assets/records.working-Cp5ualrr.js +1 -0
- package/dist/browser/assets/search-CbtiuqNx.js +1 -0
- package/dist/browser/assets/{settings-BNIy3TaP.js → settings-tVQIx1Uf.js} +1 -1
- package/dist/browser/assets/{useInfiniteQuery-03AIcFvA.js → useInfiniteQuery-C0rB-9Ci.js} +1 -1
- package/dist/browser/assets/{useKeyboardHint-DN1hAi8g.js → useKeyboardHint-D5jGavym.js} +1 -1
- package/dist/browser/index.html +24 -24
- package/dist/i18n/en/changelog.md +15 -0
- package/dist/i18n/en/docs/design.md +2 -0
- package/dist/i18n/en/docs/spec.md +30 -5
- package/dist/i18n/ko/changelog.md +15 -0
- package/dist/i18n/ko/docs/design.md +2 -0
- package/dist/i18n/ko/docs/spec.md +30 -5
- package/dist/main.js +272 -125
- package/package.json +3 -3
- package/dist/browser/assets/Selector-CGOdL2eo.js +0 -2
- package/dist/browser/assets/Token-BV_4bSkY.js +0 -2
- package/dist/browser/assets/Token-Bqkc8eyB.css +0 -1
- package/dist/browser/assets/activity-timeline-Dmc-97N6.js +0 -2
- package/dist/browser/assets/changelog-6QcNKW8u.js +0 -1
- package/dist/browser/assets/commit-BcdbBdP4.js +0 -4
- package/dist/browser/assets/contributors-B_bVSY4J.js +0 -1
- package/dist/browser/assets/dashboard.index-BFp6Hqsf.js +0 -1
- package/dist/browser/assets/document-Q3lvgyX8.js +0 -2
- package/dist/browser/assets/features-CmvypKgf.js +0 -2
- package/dist/browser/assets/features-DUHxz0_L.css +0 -1
- package/dist/browser/assets/getting-started-11zYPwlJ.js +0 -1
- package/dist/browser/assets/git-CVY8qpaV.js +0 -1
- package/dist/browser/assets/index-BeeP8ZFW.js +0 -49
- package/dist/browser/assets/index-D1JeDnJc.css +0 -1
- package/dist/browser/assets/instructions-D3-EfbZG.js +0 -1
- package/dist/browser/assets/instructions.agents-DvFHo8x8.js +0 -1
- package/dist/browser/assets/instructions.index-zHzGHq7D.js +0 -1
- package/dist/browser/assets/load-more-CymfxLt7.js +0 -1
- package/dist/browser/assets/page-header-CVCjLFQo.js +0 -246
- package/dist/browser/assets/records._recordId-Be8aM0F-.js +0 -1
- package/dist/browser/assets/records.commits._commit-Dm3gX-bQ.js +0 -1
- package/dist/browser/assets/records.index-BgfJnGAl.js +0 -1
- package/dist/browser/assets/records.working-Eeag2L5N.js +0 -1
- package/dist/browser/assets/search-CSSuO-jR.js +0 -1
package/dist/main.js
CHANGED
|
@@ -3517,6 +3517,9 @@ var messages_default = {
|
|
|
3517
3517
|
"warn.ASSET_EXTENSION": "\uBE0C\uB77C\uC6B0\uC800\uAC00 \uBBF8\uB9AC \uBCF4\uC5EC \uC8FC\uC9C0 \uC54A\uB294 \uD655\uC7A5\uC790\uB77C \uB0B4\uB824\uBC1B\uAE30\uB85C\uB9CC \uC5F4\uB9BD\uB2C8\uB2E4: {path}",
|
|
3518
3518
|
"warn.UNREFERENCED_ASSET": "\uC5B4\uB5A4 \uBB38\uC11C\uB3C4 \uAC00\uB9AC\uD0A4\uC9C0 \uC54A\uB294 \uC5D0\uC14B\uC785\uB2C8\uB2E4: {path}",
|
|
3519
3519
|
"warn.ASSETS_TOTAL_SIZE": "\uC5D0\uC14B \uC804\uCCB4\uAC00 \uAD8C\uC7A5 \uD06C\uAE30(50MB)\uB97C \uB118\uC2B5\uB2C8\uB2E4: {bytes}\uBC14\uC774\uD2B8",
|
|
3520
|
+
"warn.DESIGN_OVERVIEW_LARGE": "\uC124\uACC4 overview.md\uC758 \uC808\uC774 {sections}\uAC1C\uC785\uB2C8\uB2E4. \uB367\uBD99\uC774\uAE30 \uC804\uC5D0 \uCD95 \uD30C\uC77C\uB85C \uB098\uB20C\uC9C0 \uC0AC\uC6A9\uC790\uC5D0\uAC8C \uBB3C\uC73C\uC138\uC694(guide show design\uC758 \uAC1C\uC815): {path}",
|
|
3521
|
+
"warn.REQUIREMENT_SCOPE_FORMAT": "\uBC94\uC704\uC640 \uC81C\uC57D\uC740 \uC218\uC6A9 \uC870\uAC74 \uC55E\uC5D0 - \uBAA9\uB85D\uC73C\uB85C\uB9CC \uC501\uB2C8\uB2E4(guide show spec): {path}",
|
|
3522
|
+
"warn.REQUIREMENT_CRITERIA_FORMAT": "\uC218\uC6A9 \uC870\uAC74 \uC544\uB798\uC5D0\uB294 \uBC88\uD638 \uD56D\uBAA9\uB9CC \uB461\uB2C8\uB2E4. \uADDC\uCE59\uC740 \uBC94\uC704\uC640 \uC81C\uC57D\uC73C\uB85C \uC62E\uAE30\uC138\uC694(guide show spec): {path}",
|
|
3520
3523
|
"config.migrationRequired": "\uC774 \uD504\uB85C\uC81D\uD2B8\uB294 0.7 \uC800\uC7A5 \uADDC\uC57D(schemaVersion 2)\uC785\uB2C8\uB2E4. 0.8.0 CLI\uB294 \uC61B \uD615\uC2DD\uC744 \uC77D\uC9C0 \uC54A\uC2B5\uB2C8\uB2E4. gitifact guide show migrate\uC758 \uC808\uCC28\uB85C \uBB38\uC11C\uB97C \uC0C8 \uAD6C\uC870\uB85C \uC62E\uAE30\uC138\uC694."
|
|
3521
3524
|
};
|
|
3522
3525
|
|
|
@@ -3636,6 +3639,9 @@ var messages_default2 = {
|
|
|
3636
3639
|
"warn.ASSET_EXTENSION": "The browser does not preview this extension and offers it only as a download: {path}",
|
|
3637
3640
|
"warn.UNREFERENCED_ASSET": "No document refers to this asset: {path}",
|
|
3638
3641
|
"warn.ASSETS_TOTAL_SIZE": "All assets together are over the recommended size (50 MB): {bytes} bytes",
|
|
3642
|
+
"warn.DESIGN_OVERVIEW_LARGE": "The design overview.md has {sections} sections. Before adding to it, ask the user whether to split it into axis files (revising, in guide show design): {path}",
|
|
3643
|
+
"warn.REQUIREMENT_SCOPE_FORMAT": "Scope and constraints come before the acceptance criteria, as - items only (guide show spec): {path}",
|
|
3644
|
+
"warn.REQUIREMENT_CRITERIA_FORMAT": "The acceptance criteria hold numbered items only; move rules to scope and constraints (guide show spec): {path}",
|
|
3639
3645
|
"config.migrationRequired": "This project uses the 0.7 storage convention (schemaVersion 2). The 0.8.0 CLI does not read the old format. Move the documents to the new structure by following gitifact guide show migrate."
|
|
3640
3646
|
};
|
|
3641
3647
|
|
|
@@ -3860,20 +3866,20 @@ var scalar = (value) => {
|
|
|
3860
3866
|
fail(t("frontmatter.scalar", { value }));
|
|
3861
3867
|
return value;
|
|
3862
3868
|
};
|
|
3863
|
-
function parseFrontmatter(
|
|
3864
|
-
const legacy = new RegExp(`^<!-- ${marker}-(?:${kind2 === "wiki" ? "product|guide" : kind2}): (${legacyIds}-${token}) -->$`).exec(
|
|
3869
|
+
function parseFrontmatter(lines2, kind2, legacyIds) {
|
|
3870
|
+
const legacy = new RegExp(`^<!-- ${marker}-(?:${kind2 === "wiki" ? "product|guide" : kind2}): (${legacyIds}-${token}) -->$`).exec(lines2[0] ?? "");
|
|
3865
3871
|
if (legacy) {
|
|
3866
|
-
|
|
3872
|
+
lines2.shift();
|
|
3867
3873
|
return { id: legacy[1] };
|
|
3868
3874
|
}
|
|
3869
|
-
if (
|
|
3875
|
+
if (lines2[0] !== "---")
|
|
3870
3876
|
fail(t("frontmatter.required"));
|
|
3871
|
-
|
|
3872
|
-
const end =
|
|
3877
|
+
lines2.shift();
|
|
3878
|
+
const end = lines2.indexOf("---");
|
|
3873
3879
|
if (end === -1)
|
|
3874
3880
|
fail(t("frontmatter.unclosed"));
|
|
3875
|
-
const block =
|
|
3876
|
-
|
|
3881
|
+
const block = lines2.splice(0, end);
|
|
3882
|
+
lines2.shift();
|
|
3877
3883
|
const fields2 = /* @__PURE__ */ new Map();
|
|
3878
3884
|
for (let i = 0; i < block.length; i++) {
|
|
3879
3885
|
const line2 = block[i];
|
|
@@ -3938,17 +3944,17 @@ function validateSource(value) {
|
|
|
3938
3944
|
function parseDesign(source2, specId) {
|
|
3939
3945
|
if (source2.includes("\0") || /\r(?!\n)/.test(source2))
|
|
3940
3946
|
fail(t("design.invalidCharacters"));
|
|
3941
|
-
const
|
|
3942
|
-
const front = parseFrontmatter(
|
|
3947
|
+
const lines2 = normalized(source2).split("\n");
|
|
3948
|
+
const front = parseFrontmatter(lines2, "design", "S");
|
|
3943
3949
|
if (front.id !== specId)
|
|
3944
3950
|
fail(t("design.idMismatch"));
|
|
3945
|
-
while (
|
|
3946
|
-
|
|
3947
|
-
const heading =
|
|
3951
|
+
while (lines2[0] === "")
|
|
3952
|
+
lines2.shift();
|
|
3953
|
+
const heading = lines2.shift();
|
|
3948
3954
|
if (!heading?.startsWith("# ") || !heading.slice(2).trim())
|
|
3949
3955
|
fail(t("design.titleRequired"));
|
|
3950
3956
|
const title = heading.slice(2).trim();
|
|
3951
|
-
const raw = normalized(
|
|
3957
|
+
const raw = normalized(lines2.join("\n"));
|
|
3952
3958
|
if (!raw)
|
|
3953
3959
|
fail(t("design.bodyRequired"));
|
|
3954
3960
|
const references = /* @__PURE__ */ new Set();
|
|
@@ -3986,15 +3992,15 @@ function parseDocument(path3, source2) {
|
|
|
3986
3992
|
validateDocumentRelativePath(match[1]);
|
|
3987
3993
|
if (source2.includes("\0") || /\r(?!\n)/.test(source2))
|
|
3988
3994
|
fail(t("document.invalidCharacters", { path: path3 }));
|
|
3989
|
-
const
|
|
3990
|
-
const { id } = parseFrontmatter(
|
|
3991
|
-
while (
|
|
3992
|
-
|
|
3993
|
-
const heading =
|
|
3995
|
+
const lines2 = normalized(source2).split("\n");
|
|
3996
|
+
const { id } = parseFrontmatter(lines2, "wiki", "W");
|
|
3997
|
+
while (lines2[0] === "")
|
|
3998
|
+
lines2.shift();
|
|
3999
|
+
const heading = lines2.shift();
|
|
3994
4000
|
if (!heading?.startsWith("# ") || !heading.slice(2).trim())
|
|
3995
4001
|
fail(t("document.titleRequired", { path: path3 }));
|
|
3996
4002
|
const title = heading.slice(2).trim();
|
|
3997
|
-
const body2 = normalized(
|
|
4003
|
+
const body2 = normalized(lines2.join("\n"));
|
|
3998
4004
|
if (!body2)
|
|
3999
4005
|
fail(t("document.bodyRequired", { path: path3 }));
|
|
4000
4006
|
let fence;
|
|
@@ -4081,8 +4087,8 @@ function parseSpec(path3, source2, history = "", designSource) {
|
|
|
4081
4087
|
fail(t("spec.unsupportedPath", { path: path3 }));
|
|
4082
4088
|
if (source2.includes("\0") || source2.includes("\r") && /\r(?!\n)/.test(source2))
|
|
4083
4089
|
fail(t("spec.invalidCharacters", { path: path3 }));
|
|
4084
|
-
const
|
|
4085
|
-
const specId = parseFrontmatter(
|
|
4090
|
+
const lines2 = normalized(source2).split("\n");
|
|
4091
|
+
const specId = parseFrontmatter(lines2, "spec", "S").id;
|
|
4086
4092
|
let title = "";
|
|
4087
4093
|
let description = "";
|
|
4088
4094
|
let current2;
|
|
@@ -4095,8 +4101,8 @@ function parseSpec(path3, source2, history = "", designSource) {
|
|
|
4095
4101
|
else
|
|
4096
4102
|
description += line2 + "\n";
|
|
4097
4103
|
};
|
|
4098
|
-
for (let i = 0; i <
|
|
4099
|
-
const line2 =
|
|
4104
|
+
for (let i = 0; i < lines2.length; i++) {
|
|
4105
|
+
const line2 = lines2[i];
|
|
4100
4106
|
if (waitingId) {
|
|
4101
4107
|
const match = new RegExp(`^<!-- ${marker}-req: (R-${token}) -->$`).exec(line2);
|
|
4102
4108
|
if (!match || !current2)
|
|
@@ -4336,13 +4342,13 @@ function quoteScalar(value) {
|
|
|
4336
4342
|
return plain2 ? value : '"' + value.replace(/[\\"]/g, "\\$&") + '"';
|
|
4337
4343
|
}
|
|
4338
4344
|
function parseFrontmatterBlock(source2, path3) {
|
|
4339
|
-
const
|
|
4340
|
-
if (
|
|
4345
|
+
const lines2 = source2.split("\n");
|
|
4346
|
+
if (lines2[0] !== "---")
|
|
4341
4347
|
throw new DocumentError("FRONTMATTER_REQUIRED", path3, t("doc.FRONTMATTER_REQUIRED", { path: path3 }));
|
|
4342
|
-
const end =
|
|
4348
|
+
const end = lines2.indexOf("---", 1);
|
|
4343
4349
|
if (end === -1)
|
|
4344
4350
|
throw new DocumentError("FRONTMATTER_UNCLOSED", path3, t("doc.FRONTMATTER_UNCLOSED", { path: path3 }));
|
|
4345
|
-
const block =
|
|
4351
|
+
const block = lines2.slice(1, end);
|
|
4346
4352
|
const fields2 = /* @__PURE__ */ new Map();
|
|
4347
4353
|
const bad = (line2) => new DocumentError("FRONTMATTER_LINE", path3, t("doc.FRONTMATTER_LINE", { path: path3, line: line2 }));
|
|
4348
4354
|
for (let i = 0; i < block.length; i++) {
|
|
@@ -4385,7 +4391,7 @@ function parseFrontmatterBlock(source2, path3) {
|
|
|
4385
4391
|
throw bad(line2);
|
|
4386
4392
|
fields2.set(key, scalars.length ? { type: "list", items: scalars } : { type: "maps", items: maps });
|
|
4387
4393
|
}
|
|
4388
|
-
return { fields: fields2, body:
|
|
4394
|
+
return { fields: fields2, body: lines2.slice(end + 1).join("\n") };
|
|
4389
4395
|
}
|
|
4390
4396
|
function renderFrontmatterBlock(fields2) {
|
|
4391
4397
|
const out = ["---"];
|
|
@@ -4929,6 +4935,7 @@ function compareDocumentSets(before, after) {
|
|
|
4929
4935
|
}
|
|
4930
4936
|
|
|
4931
4937
|
// ../../packages/core/dist/use-cases/document-warnings.js
|
|
4938
|
+
var OVERVIEW_SECTION_LIMIT = 7;
|
|
4932
4939
|
function documentBodyLinks(documents) {
|
|
4933
4940
|
return documents.flatMap((doc) => extractLinks(doc.body).flatMap((link3) => {
|
|
4934
4941
|
const target = resolveLink(doc.path, link3);
|
|
@@ -4963,6 +4970,35 @@ function documentWarnings(documents, assets, existing) {
|
|
|
4963
4970
|
}
|
|
4964
4971
|
if (total > ASSETS_TOTAL_LIMIT)
|
|
4965
4972
|
warnings.push(docWarning("ASSETS_TOTAL_SIZE", ASSETS_DIR, { bytes: total }));
|
|
4973
|
+
for (const doc of documents) {
|
|
4974
|
+
if (doc.kind !== "design" || !doc.path.endsWith("/design/overview.md"))
|
|
4975
|
+
continue;
|
|
4976
|
+
const sections2 = lines(doc.body).filter((line2) => /^##\s/.test(line2)).length;
|
|
4977
|
+
if (sections2 >= OVERVIEW_SECTION_LIMIT)
|
|
4978
|
+
warnings.push(docWarning("DESIGN_OVERVIEW_LARGE", doc.path, { sections: sections2 }));
|
|
4979
|
+
}
|
|
4980
|
+
return warnings;
|
|
4981
|
+
}
|
|
4982
|
+
var lines = (body2) => body2.replace(/\r\n/g, "\n").split("\n");
|
|
4983
|
+
var scopeHeading = /^###\s+(?:범위와 제약|scope and constraints)\s*$/i;
|
|
4984
|
+
var acceptanceHeading = /^###\s+(?:수용 조건|acceptance criteria)\s*$/i;
|
|
4985
|
+
function requirementFormatWarnings(doc) {
|
|
4986
|
+
if (doc.kind !== "requirement")
|
|
4987
|
+
return [];
|
|
4988
|
+
const body2 = lines(doc.body);
|
|
4989
|
+
const scope = body2.findIndex((line2) => scopeHeading.test(line2.trim()));
|
|
4990
|
+
const acceptance = body2.findIndex((line2) => acceptanceHeading.test(line2.trim()));
|
|
4991
|
+
const sectionOf = (start) => {
|
|
4992
|
+
const rest = body2.slice(start + 1);
|
|
4993
|
+
const end = rest.findIndex((line2) => /^#{1,3}\s/.test(line2));
|
|
4994
|
+
return end < 0 ? rest : rest.slice(0, end);
|
|
4995
|
+
};
|
|
4996
|
+
const outside = (section2, item) => section2.some((line2) => line2.trim() !== "" && !item.test(line2) && !/^\s+\S/.test(line2));
|
|
4997
|
+
const warnings = [];
|
|
4998
|
+
if (scope >= 0 && (acceptance >= 0 && scope > acceptance || outside(sectionOf(scope), /^- /)))
|
|
4999
|
+
warnings.push(docWarning("REQUIREMENT_SCOPE_FORMAT", doc.path));
|
|
5000
|
+
if (acceptance >= 0 && (outside(sectionOf(acceptance), /^\d+\.\s/) || body2.slice(acceptance + 1).some((line2) => /^#{1,3}\s/.test(line2) && !scopeHeading.test(line2.trim()))))
|
|
5001
|
+
warnings.push(docWarning("REQUIREMENT_CRITERIA_FORMAT", doc.path));
|
|
4966
5002
|
return warnings;
|
|
4967
5003
|
}
|
|
4968
5004
|
|
|
@@ -4981,12 +5017,12 @@ function parseChangelog(text4) {
|
|
|
4981
5017
|
let entry2;
|
|
4982
5018
|
let section2;
|
|
4983
5019
|
const fail4 = (line2, key, values = {}) => new InitError("INVALID_CHANGELOG", t("changelog.atLine", { line: line2, reason: t(key, values) }));
|
|
4984
|
-
const
|
|
5020
|
+
const lines2 = text4.replace(/\r\n/g, "\n").split("\n");
|
|
4985
5021
|
const close = (line2) => {
|
|
4986
5022
|
if (entry2 && changelogSections.every((name2) => entry2[name2].length === 0))
|
|
4987
5023
|
throw fail4(line2, "changelog.emptyVersion", { version: entry2.version });
|
|
4988
5024
|
};
|
|
4989
|
-
|
|
5025
|
+
lines2.forEach((raw, index) => {
|
|
4990
5026
|
const line2 = index + 1;
|
|
4991
5027
|
if (raw.trim() === "")
|
|
4992
5028
|
return;
|
|
@@ -5024,7 +5060,7 @@ function parseChangelog(text4) {
|
|
|
5024
5060
|
}
|
|
5025
5061
|
throw fail4(line2, "changelog.unknownLine", { text: raw });
|
|
5026
5062
|
});
|
|
5027
|
-
close(
|
|
5063
|
+
close(lines2.length);
|
|
5028
5064
|
if (entries.length === 0)
|
|
5029
5065
|
throw fail4(1, "changelog.noVersions");
|
|
5030
5066
|
return entries;
|
|
@@ -6997,14 +7033,14 @@ function toDotPath(_path) {
|
|
|
6997
7033
|
return segs.join("");
|
|
6998
7034
|
}
|
|
6999
7035
|
function prettifyError(error62) {
|
|
7000
|
-
const
|
|
7036
|
+
const lines2 = [];
|
|
7001
7037
|
const issues = [...error62.issues].sort((a, b) => (a.path ?? []).length - (b.path ?? []).length);
|
|
7002
7038
|
for (const issue2 of issues) {
|
|
7003
|
-
|
|
7039
|
+
lines2.push(`\u2716 ${issue2.message}`);
|
|
7004
7040
|
if (issue2.path?.length)
|
|
7005
|
-
|
|
7041
|
+
lines2.push(` \u2192 at ${toDotPath(issue2.path)}`);
|
|
7006
7042
|
}
|
|
7007
|
-
return
|
|
7043
|
+
return lines2.join("\n");
|
|
7008
7044
|
}
|
|
7009
7045
|
|
|
7010
7046
|
// ../../node_modules/.pnpm/zod@4.6.4/node_modules/zod/v4/core/parse.js
|
|
@@ -7839,9 +7875,9 @@ var Doc = class {
|
|
|
7839
7875
|
return;
|
|
7840
7876
|
}
|
|
7841
7877
|
const content = arg;
|
|
7842
|
-
const
|
|
7843
|
-
const minIndent = Math.min(...
|
|
7844
|
-
const dedented =
|
|
7878
|
+
const lines2 = content.split("\n").filter((x) => x);
|
|
7879
|
+
const minIndent = Math.min(...lines2.map((x) => x.length - x.trimStart().length));
|
|
7880
|
+
const dedented = lines2.map((x) => x.slice(minIndent)).map((x) => " ".repeat(this.indent * 2) + x);
|
|
7845
7881
|
for (const line2 of dedented) {
|
|
7846
7882
|
this.content.push(line2);
|
|
7847
7883
|
}
|
|
@@ -25198,16 +25234,25 @@ var event = external_exports.strictObject({
|
|
|
25198
25234
|
after: reference,
|
|
25199
25235
|
records: external_exports.array(record2)
|
|
25200
25236
|
});
|
|
25201
|
-
var
|
|
25237
|
+
var browserHistoryV7 = external_exports.strictObject({
|
|
25202
25238
|
contract: external_exports.literal("browser-history"),
|
|
25203
|
-
version: external_exports.literal(
|
|
25239
|
+
version: external_exports.literal(7),
|
|
25204
25240
|
sessionId: external_exports.string(),
|
|
25205
25241
|
head: oid2,
|
|
25206
25242
|
// Matching changes and the commits that hold them in all of history, not in this page.
|
|
25207
25243
|
total: external_exports.number().int().nonnegative(),
|
|
25208
25244
|
commits: external_exports.number().int().nonnegative(),
|
|
25209
25245
|
next: oid2.nullable(),
|
|
25210
|
-
events: external_exports.array(event)
|
|
25246
|
+
events: external_exports.array(event),
|
|
25247
|
+
// Every document and those no record explains, and each record with how many documents it explains, in commit order.
|
|
25248
|
+
whole: external_exports.array(external_exports.strictObject({
|
|
25249
|
+
commit: oid2,
|
|
25250
|
+
documents: external_exports.number().int().nonnegative(),
|
|
25251
|
+
unrecorded: external_exports.number().int().nonnegative(),
|
|
25252
|
+
records: external_exports.array(external_exports.strictObject({ id: external_exports.string(), documents: external_exports.number().int().positive() }))
|
|
25253
|
+
})),
|
|
25254
|
+
// The kinds of document the history holds at all, so the filter offers a kind only when it can find something.
|
|
25255
|
+
kinds: external_exports.array(kind)
|
|
25211
25256
|
});
|
|
25212
25257
|
var browserHistorySummaryV5 = external_exports.strictObject({
|
|
25213
25258
|
contract: external_exports.literal("browser-history-summary"),
|
|
@@ -25243,13 +25288,14 @@ var browserSearchV3 = external_exports.strictObject({
|
|
|
25243
25288
|
});
|
|
25244
25289
|
var headQuery = oid2;
|
|
25245
25290
|
var count = (max) => external_exports.string().regex(/^(0|[1-9]\d{0,6})$/).transform(Number).pipe(external_exports.number().int().min(0).max(max));
|
|
25246
|
-
var
|
|
25291
|
+
var browserHistoryQueryV5 = external_exports.strictObject({
|
|
25247
25292
|
head: headQuery,
|
|
25248
25293
|
after: oid2.optional(),
|
|
25249
25294
|
limit: count(50).pipe(external_exports.number().min(1)).optional(),
|
|
25250
|
-
|
|
25295
|
+
// A feature or an instruction; `record=missing` keeps the changes no record explains.
|
|
25296
|
+
target: external_exports.string().regex(/^[SI]-[a-z2-7]{10}$/).optional(),
|
|
25251
25297
|
document: kind.optional(),
|
|
25252
|
-
|
|
25298
|
+
record: external_exports.literal("missing").optional(),
|
|
25253
25299
|
author: external_exports.string().min(1).max(320).optional(),
|
|
25254
25300
|
q: external_exports.string().max(200).optional()
|
|
25255
25301
|
});
|
|
@@ -25345,6 +25391,24 @@ var browserRecordV2 = external_exports.strictObject({
|
|
|
25345
25391
|
others: external_exports.number().int().nonnegative()
|
|
25346
25392
|
});
|
|
25347
25393
|
var browserRecordQueryV1 = external_exports.strictObject({ head: oid2, id: recordId });
|
|
25394
|
+
var browserDocumentHistoryV1 = external_exports.strictObject({
|
|
25395
|
+
contract: external_exports.literal("browser-document-history"),
|
|
25396
|
+
version: external_exports.literal(1),
|
|
25397
|
+
sessionId: external_exports.string(),
|
|
25398
|
+
head: oid2,
|
|
25399
|
+
doc: external_exports.strictObject({ id: external_exports.string(), title: external_exports.string().nullable(), kind: kind.nullable(), path: external_exports.string().nullable() }),
|
|
25400
|
+
total: external_exports.number().int().nonnegative(),
|
|
25401
|
+
recorded: external_exports.number().int().nonnegative(),
|
|
25402
|
+
withoutRecord: external_exports.number().int().nonnegative(),
|
|
25403
|
+
next: oid2.nullable(),
|
|
25404
|
+
events: external_exports.array(event)
|
|
25405
|
+
});
|
|
25406
|
+
var browserDocumentHistoryQueryV1 = external_exports.strictObject({
|
|
25407
|
+
head: oid2,
|
|
25408
|
+
id: external_exports.string().regex(/^[SRDWI]-[a-z2-7]{10}$/),
|
|
25409
|
+
after: oid2.optional(),
|
|
25410
|
+
limit: count(50).pipe(external_exports.number().min(1)).optional()
|
|
25411
|
+
});
|
|
25348
25412
|
var browserInstructionFileV1 = external_exports.strictObject({
|
|
25349
25413
|
contract: external_exports.literal("browser-instruction-file"),
|
|
25350
25414
|
version: external_exports.literal(1),
|
|
@@ -25635,6 +25699,7 @@ var messages_default3 = {
|
|
|
25635
25699
|
"server.cursorNotFound": "\uC774\uC5B4 \uC77D\uC744 \uC704\uCE58\uB97C \uBAA9\uB85D\uC5D0\uC11C \uCC3E\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4. \uCC98\uC74C\uBD80\uD130 \uB2E4\uC2DC \uBD88\uB7EC\uC624\uC138\uC694.",
|
|
25636
25700
|
"server.workingChangeNotFound": "\uCEE4\uBC0B \uC804 \uBCC0\uACBD\uC5D0 \uADF8 \uBB38\uC11C\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4.",
|
|
25637
25701
|
"server.recordNotFound": "\uC774 \uC774\uB825\uC5D0 \uADF8 \uACB0\uC815\uAE30\uB85D\uC774 \uC5C6\uC2B5\uB2C8\uB2E4.",
|
|
25702
|
+
"server.documentNotFound": "\uC774 \uC774\uB825\uACFC \uC791\uC5C5 \uD3F4\uB354\uC5D0 \uADF8 \uBB38\uC11C\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4.",
|
|
25638
25703
|
"server.commitFileNotFound": "\uADF8 \uCEE4\uBC0B\uC774 \uBC14\uAFBC \uD30C\uC77C\uC774 \uC544\uB2D9\uB2C8\uB2E4.",
|
|
25639
25704
|
"server.instructionFileNotFound": "\uC9C0\uCE68 \uD30C\uC77C\uC744 \uCC3E\uC744 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4.",
|
|
25640
25705
|
"server.specsUnreadable": "\uBA85\uC138\uB97C \uC77D\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4.",
|
|
@@ -25769,7 +25834,7 @@ var messages_default3 = {
|
|
|
25769
25834
|
"docs.pathExample.design": "payment/api (.gitifact/spec/payment/design/api.md)",
|
|
25770
25835
|
"docs.pathExample.instruction": "cli-architecture (.gitifact/instructions/cli-architecture/index.md)",
|
|
25771
25836
|
"docs.skeleton.feature": "(\uC774 \uAE30\uB2A5\uC774 \uBB34\uC5C7\uC774\uACE0 \uC5B4\uB514\uAE4C\uC9C0\uC778\uC9C0)",
|
|
25772
|
-
"docs.skeleton.requirement": "(\uC0AC\uC6A9\uC790)\uB85C\uC11C, (\uBAA9\uC801)\uC744 \uC704\uD574 (\uB3D9\uC791)\uC744 \uD558\uACE0 \uC2F6\uB2E4.\n\n### \uC218\uC6A9 \uC870\uAC74\n\n1. \uC870\uAC74: (\uC0C1\uD669)\n \uAE30\uB300 \uB3D9\uC791: (\uACB0\uACFC)",
|
|
25837
|
+
"docs.skeleton.requirement": "(\uC0AC\uC6A9\uC790)\uB85C\uC11C, (\uBAA9\uC801)\uC744 \uC704\uD574 (\uB3D9\uC791)\uC744 \uD558\uACE0 \uC2F6\uB2E4.\n\n### \uBC94\uC704\uC640 \uC81C\uC57D\n\n- (\uCC38\xB7\uAC70\uC9D3\uC744 \uAC00\uB9B4 \uC218 \uC788\uB294 \uADDC\uCE59 \uD55C \uBB38\uC7A5. \uC5C6\uC73C\uBA74 \uC774 \uC808\uC744 \uC9C0\uC6B4\uB2E4)\n\n### \uC218\uC6A9 \uC870\uAC74\n\n1. \uC870\uAC74: (\uC0C1\uD669)\n \uAE30\uB300 \uB3D9\uC791: (\uACB0\uACFC)",
|
|
25773
25838
|
"docs.skeleton.design": "(\uC774 \uC124\uACC4\uAC00 \uB2E4\uB8E8\uB294 \uAD6C\uC870\uC640 \uCC98\uB9AC \uBC29\uC2DD)",
|
|
25774
25839
|
"docs.skeleton.instruction": "(\uC774 \uC791\uC5C5\uC744 \uD560 \uB54C \uC9C0\uD0AC \uADDC\uCE59\uACFC \uC808\uCC28. \uC790\uC138\uD55C \uB0B4\uC6A9\uC740 references/ \uC544\uB798 \uD30C\uC77C\uB85C \uB098\uB204\uACE0 \uC5EC\uAE30\uC11C \uB9C1\uD06C\uD55C\uB2E4)",
|
|
25775
25840
|
"docs.exists": "\uC774\uBBF8 \uC788\uB294 \uD30C\uC77C\uC785\uB2C8\uB2E4: {path}",
|
|
@@ -25794,6 +25859,7 @@ var messages_default3 = {
|
|
|
25794
25859
|
"docs.singleLine": "{field}\uC740 \uD55C \uC904\uC774\uC5B4\uC57C \uD569\uB2C8\uB2E4.",
|
|
25795
25860
|
"changes.problems": "\uBB38\uC11C \uAC80\uC0AC: \uBB38\uC81C {count}\uAC1C (check\uB85C \uD655\uC778)",
|
|
25796
25861
|
"changes.warnings": "\uBB38\uC11C \uACBD\uACE0: {count}\uAC1C (check\uB85C \uD655\uC778, \uCEE4\uBC0B\uC740 \uB9C9\uC9C0 \uC54A\uC74C)",
|
|
25862
|
+
"changes.formatWarnings": "\uD615\uC2DD \uACBD\uACE0 {count}\uAC1C (\uC774\uBC88\uC5D0 \uBC14\uB010 \uC694\uAD6C\uC0AC\uD56D, \uCEE4\uBC0B\uC740 \uB9C9\uC9C0 \uC54A\uC74C)",
|
|
25797
25863
|
"changes.clean": "\uBB38\uC11C \uAC80\uC0AC: \uBB38\uC81C \uC5C6\uC74C",
|
|
25798
25864
|
"changes.pendingRecords": "\uCEE4\uBC0B\uD558\uC9C0 \uC54A\uC740 \uACB0\uC815\uAE30\uB85D {count}\uAC1C (*\uB294 \uC774\uBC88\uC5D0 \uBC14\uB00C\uC9C0 \uC54A\uC740 \uBB38\uC11C)",
|
|
25799
25865
|
"changes.withoutRecord": "\uACB0\uC815\uAE30\uB85D\uC774 \uC5C6\uB294 \uC218\uC815\xB7\uC774\uB3D9\xB7\uC0AD\uC81C: {ids}",
|
|
@@ -25949,6 +26015,7 @@ var messages_default4 = {
|
|
|
25949
26015
|
"server.cursorNotFound": "The place to read on from is no longer in the list. Load it again from the start.",
|
|
25950
26016
|
"server.workingChangeNotFound": "No uncommitted change of that document.",
|
|
25951
26017
|
"server.recordNotFound": "This history has no such decision record.",
|
|
26018
|
+
"server.documentNotFound": "Neither this history nor the working tree has that document.",
|
|
25952
26019
|
"server.commitFileNotFound": "That commit did not change this file.",
|
|
25953
26020
|
"server.instructionFileNotFound": "The instruction file was not found.",
|
|
25954
26021
|
"server.specsUnreadable": "Could not read specifications.",
|
|
@@ -26083,7 +26150,7 @@ var messages_default4 = {
|
|
|
26083
26150
|
"docs.pathExample.design": "payment/api (.gitifact/spec/payment/design/api.md)",
|
|
26084
26151
|
"docs.pathExample.instruction": "cli-architecture (.gitifact/instructions/cli-architecture/index.md)",
|
|
26085
26152
|
"docs.skeleton.feature": "(What this feature is and where it ends)",
|
|
26086
|
-
"docs.skeleton.requirement": "As (a user), I want to (act) so that (purpose).\n\n### Acceptance criteria\n\n1. Condition: (situation)\n Expected: (result)",
|
|
26153
|
+
"docs.skeleton.requirement": "As (a user), I want to (act) so that (purpose).\n\n### Scope and constraints\n\n- (One rule that is either true or false. Remove this section if there is none)\n\n### Acceptance criteria\n\n1. Condition: (situation)\n Expected: (result)",
|
|
26087
26154
|
"docs.skeleton.design": "(The structure and processing this design covers)",
|
|
26088
26155
|
"docs.skeleton.instruction": "(Rules and steps to follow for this kind of work. Put details in files under references/ and link them from here)",
|
|
26089
26156
|
"docs.exists": "The file already exists: {path}",
|
|
@@ -26108,6 +26175,7 @@ var messages_default4 = {
|
|
|
26108
26175
|
"docs.singleLine": "The {field} must be a single line.",
|
|
26109
26176
|
"changes.problems": "Document check: {count} problems (see check)",
|
|
26110
26177
|
"changes.warnings": "Document warnings: {count} (see check; they do not block a commit)",
|
|
26178
|
+
"changes.formatWarnings": "Format warnings: {count} (requirements changed here; they do not block a commit)",
|
|
26111
26179
|
"changes.clean": "Document check: no problems",
|
|
26112
26180
|
"changes.pendingRecords": "{count} uncommitted record(s) (* marks a document this change does not touch)",
|
|
26113
26181
|
"changes.withoutRecord": "Changed, moved or deleted without a record: {ids}",
|
|
@@ -26711,6 +26779,10 @@ function snippet(text4, query) {
|
|
|
26711
26779
|
return (from > 0 ? "\u2026" : "") + text4.slice(from, at + query.length + 70).trim() + (at + query.length + 70 < text4.length ? "\u2026" : "");
|
|
26712
26780
|
}
|
|
26713
26781
|
var containing = (query) => "%" + query.replace(/[\\%_]/g, (c) => "\\" + c) + "%";
|
|
26782
|
+
function hashPrefix(query) {
|
|
26783
|
+
const wanted = query?.trim().toLowerCase();
|
|
26784
|
+
return wanted && /^[0-9a-f]{7,64}$/.test(wanted) ? wanted : void 0;
|
|
26785
|
+
}
|
|
26714
26786
|
|
|
26715
26787
|
// src/adapters/cache/documents.ts
|
|
26716
26788
|
var FILE_LIMIT = 1024 * 1024;
|
|
@@ -27103,10 +27175,10 @@ function createCommitChanges(git) {
|
|
|
27103
27175
|
}
|
|
27104
27176
|
};
|
|
27105
27177
|
for (const chunk of patch.split("").filter(Boolean)) {
|
|
27106
|
-
const
|
|
27107
|
-
const commit =
|
|
27108
|
-
const removed = new Set(
|
|
27109
|
-
found.set(commit,
|
|
27178
|
+
const lines2 = chunk.split("\n");
|
|
27179
|
+
const commit = lines2[0].trim();
|
|
27180
|
+
const removed = new Set(lines2.filter((l) => l.startsWith("-") && !l.startsWith("---")).flatMap((l) => read(l.slice(1))).map((r) => r.id));
|
|
27181
|
+
found.set(commit, lines2.filter((l) => l.startsWith("+") && !l.startsWith("+++")).flatMap((l) => read(l.slice(1))).filter((r) => !removed.has(r.id)).map((r) => reasonRecord(r.id, r.docs, r.reason)));
|
|
27110
27182
|
}
|
|
27111
27183
|
return found;
|
|
27112
27184
|
}
|
|
@@ -27415,25 +27487,30 @@ function createHistory(database, git, originals) {
|
|
|
27415
27487
|
function where(filter) {
|
|
27416
27488
|
const clauses = [];
|
|
27417
27489
|
const params = [];
|
|
27418
|
-
if (filter.
|
|
27419
|
-
clauses.push("
|
|
27420
|
-
params.push(
|
|
27490
|
+
if (filter.target?.startsWith("I-")) {
|
|
27491
|
+
clauses.push("c.id = ?");
|
|
27492
|
+
params.push(filter.target);
|
|
27493
|
+
} else if (filter.target) {
|
|
27494
|
+
clauses.push("(c.before_spec = ? OR c.after_spec = ?)");
|
|
27495
|
+
params.push(filter.target, filter.target);
|
|
27421
27496
|
}
|
|
27422
27497
|
if (filter.document) {
|
|
27423
27498
|
clauses.push("c.kind = ?");
|
|
27424
27499
|
params.push(filter.document);
|
|
27425
27500
|
}
|
|
27426
|
-
if (filter.
|
|
27427
|
-
clauses.push("(c.before_spec = ? OR c.after_spec = ?)");
|
|
27428
|
-
params.push(filter.feature, filter.feature);
|
|
27429
|
-
}
|
|
27501
|
+
if (filter.unrecorded) clauses.push("json_array_length(c.row, '$.records') = 0");
|
|
27430
27502
|
if (filter.author) {
|
|
27431
27503
|
clauses.push("c.email = ?");
|
|
27432
27504
|
params.push(filter.author);
|
|
27433
27505
|
}
|
|
27434
|
-
|
|
27435
|
-
|
|
27436
|
-
|
|
27506
|
+
const q = filter.q?.trim().toLowerCase();
|
|
27507
|
+
if (q) {
|
|
27508
|
+
const record4 = `EXISTS (SELECT 1 FROM json_each(c.row, '$.records') j JOIN records r ON r.oid = c.oid AND r.id = j.value
|
|
27509
|
+
WHERE instr(lower(r.title), ?) > 0 OR instr(lower(r.id), ?) > 0
|
|
27510
|
+
OR instr(lower((SELECT group_concat(json_extract(s.value, '$.body'), ' ') FROM json_each(r.sections) s)), ?) > 0)`;
|
|
27511
|
+
const hash3 = hashPrefix(q) ? " OR substr(c.oid, 1, length(?)) = ?" : "";
|
|
27512
|
+
clauses.push(`(instr(c.needle, ?) > 0 OR ${record4}${hash3})`);
|
|
27513
|
+
params.push(q, q, q, q, ...hash3 ? [q, q] : []);
|
|
27437
27514
|
}
|
|
27438
27515
|
return { sql: clauses.map((c) => " AND " + c).join(""), params };
|
|
27439
27516
|
}
|
|
@@ -27461,11 +27538,28 @@ function createHistory(database, git, originals) {
|
|
|
27461
27538
|
const commits = db.prepare(`SELECT l.pos AS pos, l.oid AS oid ${from} AND l.pos > ? GROUP BY l.pos, l.oid ORDER BY l.pos LIMIT ?`).all(head, ...params, start, limit + 1);
|
|
27462
27539
|
const shown = commits.slice(0, limit);
|
|
27463
27540
|
const rows = !shown.length ? [] : db.prepare(`SELECT c.row ${from} AND l.pos >= ? AND l.pos <= ? ORDER BY l.pos, c.ord`).all(head, ...params, shown[0].pos, shown[shown.length - 1].pos);
|
|
27541
|
+
const oids = JSON.stringify(shown.map((c) => c.oid));
|
|
27542
|
+
const sizes = db.prepare(`SELECT oid, count(*) AS documents, sum(json_array_length(row, '$.records') = 0) AS unrecorded
|
|
27543
|
+
FROM changes WHERE oid IN (SELECT value FROM json_each(?)) GROUP BY oid`).all(oids);
|
|
27544
|
+
const explained = db.prepare(`SELECT c.oid AS oid, j.value AS id, count(*) AS documents FROM changes c, json_each(c.row, '$.records') j
|
|
27545
|
+
WHERE c.oid IN (SELECT value FROM json_each(?)) GROUP BY c.oid, j.value ORDER BY c.oid, min(c.ord)`).all(oids);
|
|
27546
|
+
const whole = shown.map(({ oid: oid3 }) => {
|
|
27547
|
+
const size = sizes.find((s) => s.oid === oid3);
|
|
27548
|
+
return {
|
|
27549
|
+
commit: oid3,
|
|
27550
|
+
documents: Number(size?.documents ?? 0),
|
|
27551
|
+
unrecorded: Number(size?.unrecorded ?? 0),
|
|
27552
|
+
records: explained.filter((r) => r.oid === oid3).map((r) => ({ id: r.id, documents: Number(r.documents) }))
|
|
27553
|
+
};
|
|
27554
|
+
});
|
|
27555
|
+
const kinds = db.prepare("SELECT DISTINCT c.kind AS kind FROM lineage l JOIN changes c ON c.oid = l.oid WHERE l.head = ?").all(head).map((k) => k.kind);
|
|
27464
27556
|
return {
|
|
27465
27557
|
total: Number(counted.n),
|
|
27466
27558
|
commits: Number(counted.commits),
|
|
27467
27559
|
next: commits.length > limit ? shown[shown.length - 1].oid : null,
|
|
27468
|
-
events: hydrate(db, rows.map((r) => r.row))
|
|
27560
|
+
events: hydrate(db, rows.map((r) => r.row)),
|
|
27561
|
+
whole,
|
|
27562
|
+
kinds
|
|
27469
27563
|
};
|
|
27470
27564
|
});
|
|
27471
27565
|
},
|
|
@@ -27515,9 +27609,11 @@ function createHistory(database, git, originals) {
|
|
|
27515
27609
|
clauses.push("(lower(json_extract(row, '$.author')) = ? OR lower(json_extract(row, '$.email')) = ?)");
|
|
27516
27610
|
params.push(filter.author.toLowerCase(), filter.author.toLowerCase());
|
|
27517
27611
|
}
|
|
27518
|
-
|
|
27519
|
-
|
|
27520
|
-
|
|
27612
|
+
const q = filter.q?.trim().toLowerCase();
|
|
27613
|
+
const hash3 = hashPrefix(q);
|
|
27614
|
+
if (q) {
|
|
27615
|
+
clauses.push(`(instr(lower(title || ' ' || id || ' ' || coalesce(body, '')), ?) > 0${hash3 ? " OR substr(oid, 1, length(?)) = ?" : ""})`);
|
|
27616
|
+
params.push(q, ...hash3 ? [hash3, hash3] : []);
|
|
27521
27617
|
}
|
|
27522
27618
|
if (filter.from !== void 0) {
|
|
27523
27619
|
clauses.push("unixepoch(json_extract(row, '$.date')) * 1000 >= ?");
|
|
@@ -27725,8 +27821,8 @@ function createCommitLog(database, git, root) {
|
|
|
27725
27821
|
* prints it. Anything shorter or not a hash names none. Newest first, a page after the commit `after`.
|
|
27726
27822
|
*/
|
|
27727
27823
|
async commitsNamed(head, raw, after, limit) {
|
|
27728
|
-
const prefix = raw
|
|
27729
|
-
if (
|
|
27824
|
+
const prefix = hashPrefix(raw);
|
|
27825
|
+
if (!prefix) return { total: 0, next: null, hits: [] };
|
|
27730
27826
|
await ensure(head);
|
|
27731
27827
|
return database.with((db) => {
|
|
27732
27828
|
const rows = db.prepare("SELECT oid, name, date, subject FROM log WHERE reach = 1 AND substr(oid, 1, length(?)) = ? ORDER BY time DESC, oid").all(prefix, prefix);
|
|
@@ -28077,6 +28173,8 @@ function createStampReader(root, inherited = process.env) {
|
|
|
28077
28173
|
const info5 = await lstat8(join9(root, ...path3.split("/"))).catch(() => void 0);
|
|
28078
28174
|
return path3 + " " + (info5 ? info5.mtimeMs + ":" + info5.size : "-");
|
|
28079
28175
|
}));
|
|
28176
|
+
const mailmap = await lstat8(join9(root, ".mailmap")).catch(() => void 0);
|
|
28177
|
+
seen.push(".mailmap " + (mailmap ? mailmap.mtimeMs + ":" + mailmap.size : "-"));
|
|
28080
28178
|
return createHash2("sha256").update(head.trim() + "\n" + seen.sort().join("\n")).digest("hex").slice(0, 20);
|
|
28081
28179
|
};
|
|
28082
28180
|
}
|
|
@@ -28152,23 +28250,23 @@ function createCheckoutReader(root, cache, inherited = process.env) {
|
|
|
28152
28250
|
return head || null;
|
|
28153
28251
|
};
|
|
28154
28252
|
const pending = /* @__PURE__ */ new Map();
|
|
28253
|
+
const last = /* @__PURE__ */ new Map();
|
|
28155
28254
|
const readStamp = createStampReader(root, inherited);
|
|
28156
|
-
async function read() {
|
|
28255
|
+
async function read(stamp) {
|
|
28157
28256
|
const raw = await readConfigFile(root);
|
|
28158
28257
|
if (!raw) throw new StoreError(t2("specReader.schemaRequired"));
|
|
28159
28258
|
parseManagedConfig(raw);
|
|
28160
28259
|
const head = await readHead();
|
|
28161
|
-
const
|
|
28162
|
-
const [current2, dirty, authors, people] = await settled([
|
|
28260
|
+
const [current3, dirty, authors, people] = await settled([
|
|
28163
28261
|
cache.documents.list(),
|
|
28164
28262
|
head ? git(["status", "--porcelain=v1", "--", ".gitifact/spec", INSTRUCTIONS_ROOT]) : Promise.resolve(""),
|
|
28165
28263
|
// Who touched each folder and who committed at all, counted over the commit log in the cache.
|
|
28166
28264
|
head ? cache.log.folders(head) : Promise.resolve(/* @__PURE__ */ new Map()),
|
|
28167
28265
|
head ? cache.log.contributors(head) : Promise.resolve([])
|
|
28168
28266
|
]);
|
|
28169
|
-
const states = await documentStates({ head: async () => head, reader },
|
|
28267
|
+
const states = await documentStates({ head: async () => head, reader }, current3.documents);
|
|
28170
28268
|
const { features, instructions: instructions2, orphans } = checkoutDocuments(states, authors);
|
|
28171
|
-
const problems = [...
|
|
28269
|
+
const problems = [...current3.problems, ...orphans.map((feature2) => docProblem("FEATURE_INDEX_REQUIRED", `.gitifact/spec/${feature2}/index.md`, { feature: feature2 }))];
|
|
28172
28270
|
if (await readHead() !== head) throw new StoreError(t2("specReader.projectChanged"));
|
|
28173
28271
|
return {
|
|
28174
28272
|
head,
|
|
@@ -28182,11 +28280,19 @@ function createCheckoutReader(root, cache, inherited = process.env) {
|
|
|
28182
28280
|
folders: authors
|
|
28183
28281
|
};
|
|
28184
28282
|
}
|
|
28283
|
+
async function current2(language) {
|
|
28284
|
+
const stamp = await readStamp();
|
|
28285
|
+
const known = last.get(language);
|
|
28286
|
+
if (known?.stamp === stamp) return { ...known, observedAt: (/* @__PURE__ */ new Date()).toISOString() };
|
|
28287
|
+
const fresh = await read(stamp);
|
|
28288
|
+
last.set(language, fresh);
|
|
28289
|
+
return fresh;
|
|
28290
|
+
}
|
|
28185
28291
|
const base = () => {
|
|
28186
28292
|
const language = getLanguage();
|
|
28187
28293
|
let value = pending.get(language);
|
|
28188
28294
|
if (!value) {
|
|
28189
|
-
value =
|
|
28295
|
+
value = current2(language).finally(() => pending.delete(language));
|
|
28190
28296
|
pending.set(language, value);
|
|
28191
28297
|
}
|
|
28192
28298
|
return value;
|
|
@@ -28240,15 +28346,15 @@ function createCommitFiles(git) {
|
|
|
28240
28346
|
const revs = parent ? [parent, commit] : [commit];
|
|
28241
28347
|
const names = (await text4([...base, "--name-status", ...revs, "--"])).split("\0");
|
|
28242
28348
|
const counts = (await text4([...base, "--numstat", ...revs, "--"])).split("\0");
|
|
28243
|
-
const
|
|
28349
|
+
const lines2 = /* @__PURE__ */ new Map();
|
|
28244
28350
|
for (let i = 0; i < counts.length; i++) {
|
|
28245
28351
|
const [added, deleted, path3] = counts[i].split(" ");
|
|
28246
28352
|
if (added === void 0 || deleted === void 0) continue;
|
|
28247
28353
|
const count2 = { additions: added === "-" ? null : Number(added), deletions: deleted === "-" ? null : Number(deleted) };
|
|
28248
28354
|
if (path3 === "") {
|
|
28249
|
-
|
|
28355
|
+
lines2.set(counts[i + 2], count2);
|
|
28250
28356
|
i += 2;
|
|
28251
|
-
} else if (path3 !== void 0)
|
|
28357
|
+
} else if (path3 !== void 0) lines2.set(path3, count2);
|
|
28252
28358
|
}
|
|
28253
28359
|
const files = [];
|
|
28254
28360
|
for (let i = 0; i < names.length - 1; i++) {
|
|
@@ -28258,7 +28364,7 @@ function createCommitFiles(git) {
|
|
|
28258
28364
|
const previousPath = renamed ? names[++i] : void 0;
|
|
28259
28365
|
const path3 = names[++i];
|
|
28260
28366
|
if (!isSource(path3) && (!previousPath || !isSource(previousPath))) continue;
|
|
28261
|
-
files.push({ path: path3, ...renamed && code.startsWith("R") ? { previousPath } : {}, status: statusOf(code), ...
|
|
28367
|
+
files.push({ path: path3, ...renamed && code.startsWith("R") ? { previousPath } : {}, status: statusOf(code), ...lines2.get(path3) ?? { additions: null, deletions: null } });
|
|
28262
28368
|
}
|
|
28263
28369
|
return { commit, parent, total: files.length, files };
|
|
28264
28370
|
}
|
|
@@ -28400,6 +28506,25 @@ async function recent(source2, head) {
|
|
|
28400
28506
|
return { group: "recent", total: hits.length, next: null, hits };
|
|
28401
28507
|
}
|
|
28402
28508
|
|
|
28509
|
+
// src/queries/document-history.ts
|
|
28510
|
+
async function documentHistory(source2, head, id) {
|
|
28511
|
+
const events = head ? await source2.cache.history.ofDocument(head, id) : [];
|
|
28512
|
+
const current2 = (await source2.cache.documents.list()).documents.find((d) => d.id === id);
|
|
28513
|
+
const last = events.map((e) => e.after ?? e.before).find(Boolean);
|
|
28514
|
+
if (!current2 && !events.length) return void 0;
|
|
28515
|
+
const doc = { id, title: current2?.title ?? last?.title ?? null, kind: current2?.kind ?? events[0]?.kind ?? null, path: current2?.path ?? last?.path ?? null };
|
|
28516
|
+
return { doc, events };
|
|
28517
|
+
}
|
|
28518
|
+
async function documentHistoryPage(source2, head, id, request) {
|
|
28519
|
+
const found = await documentHistory(source2, head, id);
|
|
28520
|
+
if (!found) return void 0;
|
|
28521
|
+
const page = pageOf(found.events, (e) => e.commit, request);
|
|
28522
|
+
if (!page) return null;
|
|
28523
|
+
const recorded = found.events.filter((e) => e.records.length).length;
|
|
28524
|
+
const withoutRecord = found.events.filter((e) => !e.records.length && e.types.some((type) => type !== "created")).length;
|
|
28525
|
+
return { doc: found.doc, total: page.total, recorded, withoutRecord, next: page.next, events: page.rows };
|
|
28526
|
+
}
|
|
28527
|
+
|
|
28403
28528
|
// src/queries/checkout.ts
|
|
28404
28529
|
var SHOWN_REQUIREMENTS = 12;
|
|
28405
28530
|
function checkoutIndex(base) {
|
|
@@ -28416,13 +28541,13 @@ function checkoutIndex(base) {
|
|
|
28416
28541
|
people: base.people.map((p) => ({ name: p.name, email: p.email }))
|
|
28417
28542
|
};
|
|
28418
28543
|
}
|
|
28419
|
-
var
|
|
28544
|
+
var acceptanceHeading2 = /^###\s+(?:수용 조건|acceptance criteria)\s*$/i;
|
|
28420
28545
|
function acceptanceCount(body2) {
|
|
28421
|
-
const
|
|
28422
|
-
const start =
|
|
28546
|
+
const lines2 = body2.replace(/\r\n/g, "\n").split("\n");
|
|
28547
|
+
const start = lines2.findIndex((line2) => acceptanceHeading2.test(line2.trim()));
|
|
28423
28548
|
if (start < 0) return null;
|
|
28424
28549
|
let count2 = 0;
|
|
28425
|
-
for (const line2 of
|
|
28550
|
+
for (const line2 of lines2.slice(start + 1)) {
|
|
28426
28551
|
if (/^#{1,6}\s/.test(line2)) break;
|
|
28427
28552
|
if (/^\d+\.\s/.test(line2)) count2++;
|
|
28428
28553
|
}
|
|
@@ -28544,10 +28669,16 @@ function recordRoutes(root, sessionId, env) {
|
|
|
28544
28669
|
} }),
|
|
28545
28670
|
// Whether the screen is behind, asked when the reader comes back to the tab; cheap enough to ask every time.
|
|
28546
28671
|
route({ method: "GET", path: "/api/v1/stamp", session: true, unreadable: unreadable2, handle: async () => ok(browserStampV1.parse({ contract: "browser-stamp", version: 1, sessionId, stamp: await readStamp() })) }),
|
|
28547
|
-
route({ method: "GET", path: "/api/v1/history", session: true, query:
|
|
28548
|
-
const page = await cache.history.commits(query.head, {
|
|
28672
|
+
route({ method: "GET", path: "/api/v1/history", session: true, query: browserHistoryQueryV5, unreadable: unreadable2, handle: async ({ query }) => {
|
|
28673
|
+
const page = await cache.history.commits(query.head, {
|
|
28674
|
+
target: query.target,
|
|
28675
|
+
document: query.document,
|
|
28676
|
+
unrecorded: query.record === "missing",
|
|
28677
|
+
author: query.author,
|
|
28678
|
+
q: query.q
|
|
28679
|
+
}, query.after, query.limit ?? PAGE);
|
|
28549
28680
|
if (!page) throw cursorGone2();
|
|
28550
|
-
return ok(
|
|
28681
|
+
return ok(browserHistoryV7.parse({ contract: "browser-history", version: 7, sessionId, head: query.head, ...page }));
|
|
28551
28682
|
} }),
|
|
28552
28683
|
route({ method: "GET", path: "/api/v1/history/summary", session: true, query: browserHistorySummaryQueryV1, unreadable: unreadable2, handle: async ({ query }) => ok(browserHistorySummaryV5.parse({
|
|
28553
28684
|
contract: "browser-history-summary",
|
|
@@ -28592,6 +28723,13 @@ function recordRoutes(root, sessionId, env) {
|
|
|
28592
28723
|
if (!found) throw new HttpError(404, "NOT_FOUND", t2("server.recordNotFound"));
|
|
28593
28724
|
return ok(browserRecordV2.parse({ contract: "browser-record", version: 2, sessionId, head: query.head, id: query.id, ...found }));
|
|
28594
28725
|
} }),
|
|
28726
|
+
// One document's decision flow in the HEAD the reader is on: the commits that changed it, a page of them at a time.
|
|
28727
|
+
route({ method: "GET", path: "/api/v1/document-history", session: true, query: browserDocumentHistoryQueryV1, unreadable: unreadable2, handle: async ({ query }) => {
|
|
28728
|
+
const found = await documentHistoryPage(source2, query.head, query.id, { after: query.after, limit: query.limit ?? PAGE });
|
|
28729
|
+
if (found === void 0) throw new HttpError(404, "NOT_FOUND", t2("server.documentNotFound"));
|
|
28730
|
+
if (found === null) throw cursorGone2();
|
|
28731
|
+
return ok(browserDocumentHistoryV1.parse({ contract: "browser-document-history", version: 1, sessionId, head: query.head, ...found }));
|
|
28732
|
+
} }),
|
|
28595
28733
|
// What is not committed yet, worked out again on every request: the uncommitted entry of the records list.
|
|
28596
28734
|
route({ method: "GET", path: "/api/v1/working", session: true, unreadable: unreadable2, handle: async () => ok(browserWorkingV1.parse({ contract: "browser-working", version: 1, sessionId, ...await workingOverview(working2) })) }),
|
|
28597
28735
|
route({ method: "GET", path: "/api/v1/working/change", session: true, query: browserWorkingChangeQueryV1, unreadable: unreadable2, handle: async ({ query }) => {
|
|
@@ -28973,11 +29111,11 @@ import { readFile as readFile11 } from "node:fs/promises";
|
|
|
28973
29111
|
// src/commands/output.ts
|
|
28974
29112
|
var formats = ["text", "json"];
|
|
28975
29113
|
var CommandError = class extends Error {
|
|
28976
|
-
constructor(code, message, details = {},
|
|
29114
|
+
constructor(code, message, details = {}, lines2 = []) {
|
|
28977
29115
|
super(message);
|
|
28978
29116
|
this.code = code;
|
|
28979
29117
|
this.details = details;
|
|
28980
|
-
this.lines =
|
|
29118
|
+
this.lines = lines2;
|
|
28981
29119
|
}
|
|
28982
29120
|
code;
|
|
28983
29121
|
details;
|
|
@@ -28994,13 +29132,13 @@ async function runCommand(contract, format2, run) {
|
|
|
28994
29132
|
const code = known ? error62.code : contract.toUpperCase() + "_FAILED";
|
|
28995
29133
|
const message = known ? error62.message : t2("command.failed");
|
|
28996
29134
|
const details = error62 instanceof CommandError ? error62.details : {};
|
|
28997
|
-
const
|
|
28998
|
-
process.stderr.write(format2 === "json" ? JSON.stringify({ ...envelope, ok: false, error: { code, message, ...details } }) + "\n" : [code + ": " + message, ...
|
|
29135
|
+
const lines2 = error62 instanceof CommandError ? error62.lines : [];
|
|
29136
|
+
process.stderr.write(format2 === "json" ? JSON.stringify({ ...envelope, ok: false, error: { code, message, ...details } }) + "\n" : [code + ": " + message, ...lines2].join("\n") + "\n");
|
|
28999
29137
|
process.exitCode = 1;
|
|
29000
29138
|
}
|
|
29001
29139
|
}
|
|
29002
|
-
var section = (label,
|
|
29003
|
-
var text2 = (
|
|
29140
|
+
var section = (label, lines2, indent = " ") => lines2.length ? [label, ...lines2.map((line2) => indent + line2)] : [];
|
|
29141
|
+
var text2 = (lines2) => lines2.join("\n") + "\n";
|
|
29004
29142
|
|
|
29005
29143
|
// src/commands/guide.ts
|
|
29006
29144
|
var guideTopics = ["workflow", "spec", "design", "instructions", "records", "writing", "commit", "migrate"];
|
|
@@ -29071,8 +29209,8 @@ function findBlock(text4) {
|
|
|
29071
29209
|
function isWrapperFile(text4) {
|
|
29072
29210
|
const found = findBlock(text4);
|
|
29073
29211
|
const own2 = found ? text4.slice(0, found.start) + text4.slice(found.end) : text4;
|
|
29074
|
-
const
|
|
29075
|
-
return
|
|
29212
|
+
const lines2 = own2.split(/\r?\n/).map((line2) => line2.trim()).filter(Boolean);
|
|
29213
|
+
return lines2.length > 0 && lines2.every((line2) => /^@(?:\.\/)?[^\s]+$/.test(line2) && candidatePaths.includes(line2.replace(/^@(?:\.\/)?/, "")));
|
|
29076
29214
|
}
|
|
29077
29215
|
var CLAUDE_WRAPPER_PATH = "CLAUDE.md";
|
|
29078
29216
|
function claudeWrapperFor(agents2) {
|
|
@@ -29732,8 +29870,8 @@ function cursorGone(options) {
|
|
|
29732
29870
|
throw new CommandError("INVALID_VALUE", t2("list.after", { cursor: options.after ?? "" }));
|
|
29733
29871
|
}
|
|
29734
29872
|
var pageLine = (page, before = 0, unit = t2("list.items")) => page.next === null ? [] : [t2("list.more", { shown: before + page.rows.length, total: page.total, unit, cursor: page.next })];
|
|
29735
|
-
function aside(format2,
|
|
29736
|
-
if (format2 === "text" &&
|
|
29873
|
+
function aside(format2, lines2) {
|
|
29874
|
+
if (format2 === "text" && lines2.length) process.stderr.write(lines2.join("\n") + "\n");
|
|
29737
29875
|
return "";
|
|
29738
29876
|
}
|
|
29739
29877
|
|
|
@@ -30136,6 +30274,10 @@ var recordLine = (r, changes2) => {
|
|
|
30136
30274
|
const changed = new Set(changes2.map((c) => c.id));
|
|
30137
30275
|
return `${r.id} ${r.title}${r.draft ? " (" + t2("docs.draft") + ")" : ""} \u2014 ${r.docs.map((d) => changed.has(d) ? d : d + "*").join(", ")}`;
|
|
30138
30276
|
};
|
|
30277
|
+
var formatWarnings = (changes2, documents) => {
|
|
30278
|
+
const touched = new Set(changes2.map((c) => c.id));
|
|
30279
|
+
return documents.filter((d) => touched.has(d.id)).flatMap(requirementFormatWarnings);
|
|
30280
|
+
};
|
|
30139
30281
|
var recordSummary = (r) => ({ id: r.id, title: r.title, docs: r.docs, path: r.path, ...r.draft ? { draft: true } : {} });
|
|
30140
30282
|
var runChangesList = (options, controls = {}) => runCommand("changes", options.format, async () => {
|
|
30141
30283
|
const project = await openProject(process.cwd());
|
|
@@ -30146,7 +30288,8 @@ var runChangesList = (options, controls = {}) => runCommand("changes", options.f
|
|
|
30146
30288
|
const withoutRecord = uncovered(changes2, records2);
|
|
30147
30289
|
const sharedDocuments = shared(changes2, records2);
|
|
30148
30290
|
const problems = [...working2.problems, ...pending.problems, ...checked.problems];
|
|
30149
|
-
const
|
|
30291
|
+
const formats2 = formatWarnings(changes2, checked.documents);
|
|
30292
|
+
const warnings = [...await readDocumentWarnings(project.root, checked.documents), ...formats2];
|
|
30150
30293
|
const inputs = await prepareAgentInputs(project.root, controls).catch(() => void 0);
|
|
30151
30294
|
const out = changes2.length ? [t2("changes.changed", { count: changes2.length }), ...changes2.map((c) => " " + changeLine(c))] : [t2("changes.none")];
|
|
30152
30295
|
out.push(...section(t2("changes.pendingRecords", { count: records2.length }), records2.map((r) => recordLine(r, changes2))));
|
|
@@ -30154,7 +30297,8 @@ var runChangesList = (options, controls = {}) => runCommand("changes", options.f
|
|
|
30154
30297
|
if (sharedDocuments.length) out.push(t2("changes.sharedDocuments", { ids: sharedDocuments.join(", ") }));
|
|
30155
30298
|
if (pending.altered.length) out.push(t2("changes.recordAltered", { paths: pending.altered.join(", ") }));
|
|
30156
30299
|
out.push(problems.length ? t2("changes.problems", { count: problems.length }) : t2("changes.clean"));
|
|
30157
|
-
if (warnings.length) out.push(t2("changes.warnings", { count: warnings.length }));
|
|
30300
|
+
if (warnings.length > formats2.length) out.push(t2("changes.warnings", { count: warnings.length - formats2.length }));
|
|
30301
|
+
out.push(...section(t2("changes.formatWarnings", { count: formats2.length }), formats2.map((w) => w.code + " " + w.message)));
|
|
30158
30302
|
if (inputs) out.push(t2("changes.input", { path: inputs.commit }));
|
|
30159
30303
|
return { json: { head, changes: changes2, pendingRecords: records2.map(recordSummary), withoutRecord, sharedDocuments, alteredRecords: pending.altered, problems, warnings, inputs: inputs ?? null }, text: text2(out) };
|
|
30160
30304
|
});
|
|
@@ -30169,6 +30313,7 @@ var runChangesCommit = (options, controls = {}) => runCommand("changes", options
|
|
|
30169
30313
|
...result.changes.map((c) => " " + changeLine(c)),
|
|
30170
30314
|
...result.records.map((r) => " " + r.id + " " + r.title),
|
|
30171
30315
|
...result.withoutRecord.length ? [t2("changes.withoutRecord", { ids: result.withoutRecord.join(", ") })] : [],
|
|
30316
|
+
...section(t2("changes.formatWarnings", { count: result.warnings.length }), result.warnings.map((w) => w.code + " " + w.message)),
|
|
30172
30317
|
...result.trailers
|
|
30173
30318
|
];
|
|
30174
30319
|
return { json: { ...json3, ...inputRemoved === void 0 ? {} : { inputRemoved } }, text: text2(out) };
|
|
@@ -30225,6 +30370,7 @@ async function commitChanges(cwd, input2, dryRun) {
|
|
|
30225
30370
|
const split = changes2.filter((c) => c.previousPath !== void 0 && !(selected2.includes(c.path) && selected2.includes(c.previousPath)));
|
|
30226
30371
|
if (split.length) fail3(t2("commit.selectMove", { ids: split.map((c) => c.id).join(", ") }));
|
|
30227
30372
|
const withoutRecord = uncovered(changes2, records2);
|
|
30373
|
+
const warnings = formatWarnings(changes2, checked.documents);
|
|
30228
30374
|
const status = (await git(["status", "--porcelain=v1", "-z", "--untracked-files=all", "--no-renames", "--", ".gitifact"])).toString("utf8").split("\0").filter(Boolean);
|
|
30229
30375
|
const removed = new Set(status.filter((entry2) => entry2.slice(0, 2).includes("D")).map((entry2) => entry2.slice(3)));
|
|
30230
30376
|
checkStoreSelection(selected2.filter((p) => !(underDocuments(p) && removed.has(p))));
|
|
@@ -30241,7 +30387,7 @@ async function commitChanges(cwd, input2, dryRun) {
|
|
|
30241
30387
|
const contextPaths = policyPaths(selected2);
|
|
30242
30388
|
const hashes = async (list) => new Map(await Promise.all(list.map(async (p) => [p, await fingerprint(root, p)])));
|
|
30243
30389
|
const started = await hashes([.../* @__PURE__ */ new Set([...selected2, ...contextPaths])]);
|
|
30244
|
-
const summary = { root, head: base.head, message, paths: selected2, changes: changes2, records: records2.map(recordSummary), withoutRecord, trailers };
|
|
30390
|
+
const summary = { root, head: base.head, message, paths: selected2, changes: changes2, records: records2.map(recordSummary), withoutRecord, warnings, trailers };
|
|
30245
30391
|
if (dryRun) {
|
|
30246
30392
|
if (!same2(base, await project.reader.baseline())) fail3(t2("commit.headChanged"));
|
|
30247
30393
|
return { outcome: "dry-run", committed: false, ...summary, commit: void 0 };
|
|
@@ -30406,12 +30552,13 @@ var runRecordsList = (options) => runCommand("records", options.format, async ()
|
|
|
30406
30552
|
const after = await since(project, options.since, head);
|
|
30407
30553
|
const by = byAuthor(options.author);
|
|
30408
30554
|
const has2 = contains(options.q);
|
|
30555
|
+
const hash3 = hashPrefix(options.q);
|
|
30409
30556
|
const id = options.doc;
|
|
30410
|
-
const
|
|
30411
|
-
|
|
30412
|
-
const
|
|
30413
|
-
|
|
30414
|
-
const page = paginate(events.filter((e) => after(e) && by(e) && has2(
|
|
30557
|
+
const found2 = await documentHistory(project, head, id);
|
|
30558
|
+
if (!found2) throw new CommandError("UNKNOWN_DOCUMENT", t2("docs.unknownDocument", { ids: id }));
|
|
30559
|
+
const { events } = found2;
|
|
30560
|
+
const title = found2.doc.title;
|
|
30561
|
+
const page = paginate(events.filter((e) => after(e) && by(e) && (has2(...e.records.flatMap((r) => [r.title, r.id, ...sectionText(r.sections)])) || !!hash3 && e.commit.startsWith(hash3))).map((e) => ({
|
|
30415
30562
|
commit: e.commit,
|
|
30416
30563
|
date: e.date,
|
|
30417
30564
|
author: e.author,
|
|
@@ -30449,7 +30596,7 @@ var runRecordsList = (options) => runCommand("records", options.format, async ()
|
|
|
30449
30596
|
} catch {
|
|
30450
30597
|
return [];
|
|
30451
30598
|
}
|
|
30452
|
-
}).map((r) => ({ id: r.id, title: r.title, commit: null, date: null, author: null, docs: r.docs, sections: r.sections.map((s) => ({ key: s.key, body: s.body })) }))).filter((r) => has(r.title, ...sectionText(r.sections))).sort((a, b) => a.id < b.id ? -1 : 1);
|
|
30599
|
+
}).map((r) => ({ id: r.id, title: r.title, commit: null, date: null, author: null, docs: r.docs, sections: r.sections.map((s) => ({ key: s.key, body: s.body })) }))).filter((r) => has(r.title, r.id, ...sectionText(r.sections))).sort((a, b) => a.id < b.id ? -1 : 1);
|
|
30453
30600
|
const size = options.all ? void 0 : options.limit ?? PAGE_SIZE;
|
|
30454
30601
|
const inPending = options.after === void 0 ? 0 : pending.findIndex((r) => r.id === options.after) + 1;
|
|
30455
30602
|
const afterCommitted = options.after !== void 0 && !inPending ? options.after : void 0;
|
|
@@ -30759,23 +30906,23 @@ async function runUpdate(options, version2) {
|
|
|
30759
30906
|
process.stdout.write(JSON.stringify(dto) + "\n");
|
|
30760
30907
|
return;
|
|
30761
30908
|
}
|
|
30762
|
-
const
|
|
30763
|
-
|
|
30764
|
-
if (dto.install)
|
|
30765
|
-
|
|
30766
|
-
if (dto.agentDocs.missing.length)
|
|
30767
|
-
if (dto.project.state === "written")
|
|
30768
|
-
if (dto.project.cli && isNewerRelease(dto.project.cli, dto.cliVersion))
|
|
30769
|
-
if (dto.migrationRequired)
|
|
30909
|
+
const lines2 = [t2("update.text.current", { version: dto.cliVersion })];
|
|
30910
|
+
lines2.push(dto.update.status === "available" ? t2("update.text.available", { version: dto.update.latestVersion }) : dto.update.status === "up-to-date" ? t2("update.text.upToDate") : dto.update.status === "disabled" ? t2("update.text.disabled") : t2("update.text.unavailable"));
|
|
30911
|
+
if (dto.install) lines2.push(t2("update.text.install", { command: dto.install.npmGlobal }), t2("update.text.afterInstall"));
|
|
30912
|
+
lines2.push(dto.agentDocs.state === "refreshed" ? t2("update.text.blockRefreshed", { paths: dto.agentDocs.paths.join(", ") }) : dto.agentDocs.state === "current" ? t2("update.text.blockCurrent", { paths: dto.agentDocs.paths.join(", ") }) : dto.agentDocs.state === "kept" ? t2("update.text.blockKept", { paths: dto.agentDocs.paths.join(", ") || "-" }) : dto.agentDocs.state === "no-block" ? t2("update.text.noBlock") : t2("update.text.notInitialized"));
|
|
30913
|
+
if (dto.agentDocs.missing.length) lines2.push(t2("update.text.missing", { paths: dto.agentDocs.missing.join(", ") }));
|
|
30914
|
+
if (dto.project.state === "written") lines2.push(t2("update.text.projectWritten", { path: CONFIG_PATH, version: dto.project.cli ?? dto.cliVersion }));
|
|
30915
|
+
if (dto.project.cli && isNewerRelease(dto.project.cli, dto.cliVersion)) lines2.push(t2("update.text.projectAhead", { project: dto.project.cli, version: dto.cliVersion, command: npmGlobalInstall(dto.project.cli) }));
|
|
30916
|
+
if (dto.migrationRequired) lines2.push(t2("update.text.migrationRequired", { version: dto.cliVersion }));
|
|
30770
30917
|
const { commit } = dto;
|
|
30771
|
-
if (commit.state === "committed")
|
|
30772
|
-
else if (commit.state === "nothing")
|
|
30918
|
+
if (commit.state === "committed") lines2.push(t2("update.text.committed", { commit: commit.commit.slice(0, 12), paths: commit.paths.join(", ") }));
|
|
30919
|
+
else if (commit.state === "nothing") lines2.push(t2("update.text.commitNothing"));
|
|
30773
30920
|
else if (commit.state === "skipped") {
|
|
30774
30921
|
const paths2 = commit.paths.join(", ");
|
|
30775
30922
|
const text4 = commit.reason === "untracked" ? t2("update.text.commitSkipped.untracked", { paths: paths2 }) : commit.reason === "other-changes" ? t2("update.text.commitSkipped.other-changes", { paths: paths2 }) : t2("update.text.commitSkipped.commit-failed", { paths: paths2 });
|
|
30776
|
-
|
|
30923
|
+
lines2.push(text4 + (commit.detail ? " (" + commit.detail + ")" : ""));
|
|
30777
30924
|
}
|
|
30778
|
-
process.stdout.write(
|
|
30925
|
+
process.stdout.write(lines2.join("\n") + "\n");
|
|
30779
30926
|
} catch (error62) {
|
|
30780
30927
|
const known = error62 instanceof InitError || error62 instanceof RepositoryReadError;
|
|
30781
30928
|
const failure2 = { code: known ? error62.code : "UPDATE_FAILED", message: known ? error62.message : t2("update.failed") };
|
|
@@ -30804,12 +30951,12 @@ async function runUpdateCheck(format2, version2) {
|
|
|
30804
30951
|
return;
|
|
30805
30952
|
}
|
|
30806
30953
|
const state2 = dto.update;
|
|
30807
|
-
const
|
|
30954
|
+
const lines2 = [
|
|
30808
30955
|
t2("update.text.current", { version: dto.cliVersion }),
|
|
30809
30956
|
state2.status === "available" ? t2("update.text.available", { version: state2.latestVersion }) : state2.status === "up-to-date" ? t2("update.text.upToDate") : state2.status === "disabled" ? t2("update.text.disabled") : t2("update.text.unavailable")
|
|
30810
30957
|
];
|
|
30811
|
-
if (state2.status === "available")
|
|
30812
|
-
process.stdout.write(
|
|
30958
|
+
if (state2.status === "available") lines2.push(t2("update.text.install", { command: npmGlobalInstall(state2.latestVersion) }), t2("update.text.afterInstall"));
|
|
30959
|
+
process.stdout.write(lines2.join("\n") + "\n");
|
|
30813
30960
|
}
|
|
30814
30961
|
|
|
30815
30962
|
// src/commands/version-notice.ts
|
|
@@ -30884,17 +31031,17 @@ for (let i = 0; i < languageArgs.length; i++) {
|
|
|
30884
31031
|
if (value === "ko" || value === "en") selectedLanguage = value;
|
|
30885
31032
|
}
|
|
30886
31033
|
configureLanguage(selectedLanguage ?? environmentLanguage(), selectedLanguage);
|
|
30887
|
-
var program2 = new Command().name("gitifact").addOption(new Option("--lang <language>", t2("help.lang")).choices(["ko", "en"])).description(t2("help.program")).version("0.8.
|
|
31034
|
+
var program2 = new Command().name("gitifact").addOption(new Option("--lang <language>", t2("help.lang")).choices(["ko", "en"])).description(t2("help.program")).version("0.8.5").allowExcessArguments(false).addHelpText("after", "\n" + t2("help.notYet")).action(() => program2.outputHelp());
|
|
30888
31035
|
program2.hook("preAction", async (_program, action) => {
|
|
30889
31036
|
let top = action;
|
|
30890
31037
|
while (top.parent && top.parent !== program2) top = top.parent;
|
|
30891
|
-
if (top.name() !== REFRESH_COMMAND) await noticeVersion("0.8.
|
|
31038
|
+
if (top.name() !== REFRESH_COMMAND) await noticeVersion("0.8.5", top.name());
|
|
30892
31039
|
});
|
|
30893
|
-
program2.command(REFRESH_COMMAND, { hidden: true }).allowExcessArguments(false).action(() => refreshUpdateCache("0.8.
|
|
31040
|
+
program2.command(REFRESH_COMMAND, { hidden: true }).allowExcessArguments(false).action(() => refreshUpdateCache("0.8.5"));
|
|
30894
31041
|
var format = () => new Option("--format <format>", t2("help.format")).choices(formats).default("text");
|
|
30895
|
-
program2.command("browser").description(t2("help.browser")).allowExcessArguments(false).option("--port <port>", t2("help.browserPort"), parsePort, 0).option("--dev", t2("help.browserDev")).action((options) => runBrowser(options, "0.8.
|
|
30896
|
-
program2.command("init").description(t2("help.init")).allowExcessArguments(false).option("--dry-run", t2("help.initDryRun")).addOption(new Option("--agent <agent>", t2("help.initAgent")).choices([...agentPresetNames])).addOption(new Option("--remove-agents", t2("help.initRemoveAgents")).conflicts("skipAgents")).option("--skip-agents", t2("help.initSkipAgents")).addOption(new Option("--format <format>", t2("help.format")).choices(["json", "text"]).default("json")).action((options) => runInit(options, "0.8.
|
|
30897
|
-
program2.command("update").description(t2("help.update")).allowExcessArguments(false).addOption(new Option("--format <format>", t2("help.format")).choices(["json", "text"]).default("json")).option("--commit", t2("help.updateCommit")).addOption(new Option("--check", t2("help.updateCheck")).conflicts("commit")).addOption(new Option("--later", t2("help.updateLater")).conflicts(["check", "commit"])).action((options) => options.later ? runUpdateLater(options.format, "0.8.
|
|
31042
|
+
program2.command("browser").description(t2("help.browser")).allowExcessArguments(false).option("--port <port>", t2("help.browserPort"), parsePort, 0).option("--dev", t2("help.browserDev")).action((options) => runBrowser(options, "0.8.5"));
|
|
31043
|
+
program2.command("init").description(t2("help.init")).allowExcessArguments(false).option("--dry-run", t2("help.initDryRun")).addOption(new Option("--agent <agent>", t2("help.initAgent")).choices([...agentPresetNames])).addOption(new Option("--remove-agents", t2("help.initRemoveAgents")).conflicts("skipAgents")).option("--skip-agents", t2("help.initSkipAgents")).addOption(new Option("--format <format>", t2("help.format")).choices(["json", "text"]).default("json")).action((options) => runInit(options, "0.8.5"));
|
|
31044
|
+
program2.command("update").description(t2("help.update")).allowExcessArguments(false).addOption(new Option("--format <format>", t2("help.format")).choices(["json", "text"]).default("json")).option("--commit", t2("help.updateCommit")).addOption(new Option("--check", t2("help.updateCheck")).conflicts("commit")).addOption(new Option("--later", t2("help.updateLater")).conflicts(["check", "commit"])).action((options) => options.later ? runUpdateLater(options.format, "0.8.5") : options.check ? runUpdateCheck(options.format, "0.8.5") : runUpdate(options, "0.8.5"));
|
|
30898
31045
|
var listed2 = (command, sorts) => {
|
|
30899
31046
|
command.allowExcessArguments(false).option("--q <words>", t2("help.listQ")).option("--author <name>", t2("help.listAuthor"));
|
|
30900
31047
|
if (sorts) command.addOption(new Option("--sort <key>", t2("help.listSort")).choices([...sorts]).default(sorts[0]));
|
|
@@ -30916,7 +31063,7 @@ program2.command("check").description(t2("help.check")).allowExcessArguments(fal
|
|
|
30916
31063
|
var changes = program2.command("changes").description(t2("help.changes"));
|
|
30917
31064
|
changes.command("list").description(t2("help.changesList")).allowExcessArguments(false).addOption(format()).action((o) => runChangesList(o));
|
|
30918
31065
|
changes.command("commit").description(t2("help.changesCommit")).allowExcessArguments(false).requiredOption("--file <path>", t2("help.changesCommitFile")).option("--dry-run", t2("help.changesCommitDryRun")).addOption(format()).action((o) => runChangesCommit(o));
|
|
30919
|
-
program2.command("feedback").description(t2("help.feedback")).allowExcessArguments(false).requiredOption("--file <path>", t2("help.feedbackFile")).option("--dry-run", t2("help.feedbackDryRun")).addOption(format()).action((o) => runFeedback(o, "0.8.
|
|
31066
|
+
program2.command("feedback").description(t2("help.feedback")).allowExcessArguments(false).requiredOption("--file <path>", t2("help.feedbackFile")).option("--dry-run", t2("help.feedbackDryRun")).addOption(format()).action((o) => runFeedback(o, "0.8.5"));
|
|
30920
31067
|
var guide = program2.command("guide").description(t2("help.guide"));
|
|
30921
31068
|
guide.command("list").description(t2("help.guideList")).allowExcessArguments(false).addOption(format()).action((o) => runGuideList(o));
|
|
30922
31069
|
guide.command("show").description(t2("help.guideShow")).argument("<topic>", t2("help.guideTopic")).allowExcessArguments(false).addOption(format()).action((topic, o) => runGuideShow(topic, o));
|