qfai 0.3.3 → 0.3.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.
Files changed (165) hide show
  1. package/README.md +2 -2
  2. package/assets/init/.qfai/README.md +11 -0
  3. package/assets/init/.qfai/promptpack/commands/implement.md +6 -0
  4. package/assets/init/.qfai/promptpack/commands/plan.md +9 -0
  5. package/assets/init/.qfai/promptpack/commands/release.md +6 -0
  6. package/assets/init/.qfai/promptpack/commands/review.md +6 -0
  7. package/assets/init/.qfai/promptpack/constitution.md +15 -0
  8. package/assets/init/.qfai/promptpack/modes/change.md +4 -0
  9. package/assets/init/.qfai/promptpack/modes/compatibility.md +4 -0
  10. package/assets/init/.qfai/promptpack/roles/qa.md +4 -0
  11. package/assets/init/.qfai/promptpack/roles/spec.md +4 -0
  12. package/assets/init/.qfai/promptpack/roles/test.md +4 -0
  13. package/assets/init/.qfai/promptpack/steering/compatibility-vs-change.md +8 -0
  14. package/assets/init/.qfai/promptpack/steering/naming.md +7 -0
  15. package/assets/init/.qfai/promptpack/steering/traceability.md +9 -0
  16. package/assets/init/.qfai/prompts/require-to-spec.md +4 -4
  17. package/assets/init/.qfai/require/README.md +28 -0
  18. package/assets/init/.qfai/rules/conventions.md +6 -0
  19. package/dist/cli/commands/init.d.ts +8 -0
  20. package/dist/cli/commands/init.d.ts.map +1 -0
  21. package/dist/cli/commands/init.js +30 -0
  22. package/dist/cli/commands/init.js.map +1 -0
  23. package/dist/cli/commands/report.d.ts +7 -0
  24. package/dist/cli/commands/report.d.ts.map +1 -0
  25. package/dist/cli/commands/report.js +87 -0
  26. package/dist/cli/commands/report.js.map +1 -0
  27. package/dist/cli/commands/validate.d.ts +9 -0
  28. package/dist/cli/commands/validate.d.ts.map +1 -0
  29. package/dist/cli/commands/validate.js +57 -0
  30. package/dist/cli/commands/validate.js.map +1 -0
  31. package/dist/cli/index.cjs +2 -2
  32. package/dist/cli/index.d.ts +2 -0
  33. package/dist/cli/index.d.ts.map +1 -0
  34. package/dist/cli/index.js +7 -0
  35. package/dist/cli/index.js.map +1 -0
  36. package/dist/cli/index.mjs +2 -2
  37. package/dist/cli/lib/args.d.ts +18 -0
  38. package/dist/cli/lib/args.d.ts.map +1 -0
  39. package/dist/cli/lib/args.js +98 -0
  40. package/dist/cli/lib/args.js.map +1 -0
  41. package/dist/cli/lib/assets.d.ts +2 -0
  42. package/dist/cli/lib/assets.d.ts.map +1 -0
  43. package/dist/cli/lib/assets.js +24 -0
  44. package/dist/cli/lib/assets.js.map +1 -0
  45. package/dist/cli/lib/failOn.d.ts +5 -0
  46. package/dist/cli/lib/failOn.d.ts.map +1 -0
  47. package/dist/cli/lib/failOn.js +10 -0
  48. package/dist/cli/lib/failOn.js.map +1 -0
  49. package/dist/cli/lib/fs.d.ts +11 -0
  50. package/dist/cli/lib/fs.d.ts.map +1 -0
  51. package/dist/cli/lib/fs.js +91 -0
  52. package/dist/cli/lib/fs.js.map +1 -0
  53. package/dist/cli/lib/logger.d.ts +4 -0
  54. package/dist/cli/lib/logger.d.ts.map +1 -0
  55. package/dist/cli/lib/logger.js +10 -0
  56. package/dist/cli/lib/logger.js.map +1 -0
  57. package/dist/cli/main.d.ts +2 -0
  58. package/dist/cli/main.d.ts.map +1 -0
  59. package/dist/cli/main.js +66 -0
  60. package/dist/cli/main.js.map +1 -0
  61. package/dist/core/config.d.ts +44 -0
  62. package/dist/core/config.d.ts.map +1 -0
  63. package/dist/core/config.js +218 -0
  64. package/dist/core/config.js.map +1 -0
  65. package/dist/core/contractIndex.d.ts +13 -0
  66. package/dist/core/contractIndex.d.ts.map +1 -0
  67. package/dist/core/contractIndex.js +66 -0
  68. package/dist/core/contractIndex.js.map +1 -0
  69. package/dist/core/contracts.d.ts +5 -0
  70. package/dist/core/contracts.d.ts.map +1 -0
  71. package/dist/core/contracts.js +42 -0
  72. package/dist/core/contracts.js.map +1 -0
  73. package/dist/core/discovery.d.ts +14 -0
  74. package/dist/core/discovery.d.ts.map +1 -0
  75. package/dist/core/discovery.js +55 -0
  76. package/dist/core/discovery.js.map +1 -0
  77. package/dist/core/fs.d.ts +6 -0
  78. package/dist/core/fs.d.ts.map +1 -0
  79. package/dist/core/fs.js +55 -0
  80. package/dist/core/fs.js.map +1 -0
  81. package/dist/core/gherkin/parse.d.ts +7 -0
  82. package/dist/core/gherkin/parse.d.ts.map +1 -0
  83. package/dist/core/gherkin/parse.js +25 -0
  84. package/dist/core/gherkin/parse.js.map +1 -0
  85. package/dist/core/ids.d.ts +6 -0
  86. package/dist/core/ids.d.ts.map +1 -0
  87. package/dist/core/ids.js +52 -0
  88. package/dist/core/ids.js.map +1 -0
  89. package/dist/core/index.d.ts +13 -0
  90. package/dist/core/index.d.ts.map +1 -0
  91. package/dist/core/index.js +13 -0
  92. package/dist/core/index.js.map +1 -0
  93. package/dist/core/parse/adr.d.ts +13 -0
  94. package/dist/core/parse/adr.d.ts.map +1 -0
  95. package/dist/core/parse/adr.js +33 -0
  96. package/dist/core/parse/adr.js.map +1 -0
  97. package/dist/core/parse/gherkin.d.ts +12 -0
  98. package/dist/core/parse/gherkin.d.ts.map +1 -0
  99. package/dist/core/parse/gherkin.js +22 -0
  100. package/dist/core/parse/gherkin.js.map +1 -0
  101. package/dist/core/parse/markdown.d.ts +14 -0
  102. package/dist/core/parse/markdown.d.ts.map +1 -0
  103. package/dist/core/parse/markdown.js +45 -0
  104. package/dist/core/parse/markdown.js.map +1 -0
  105. package/dist/core/parse/spec.d.ts +28 -0
  106. package/dist/core/parse/spec.d.ts.map +1 -0
  107. package/dist/core/parse/spec.js +80 -0
  108. package/dist/core/parse/spec.js.map +1 -0
  109. package/dist/core/report.d.ts +39 -0
  110. package/dist/core/report.d.ts.map +1 -0
  111. package/dist/core/report.js +226 -0
  112. package/dist/core/report.js.map +1 -0
  113. package/dist/core/scenarioModel.d.ts +33 -0
  114. package/dist/core/scenarioModel.d.ts.map +1 -0
  115. package/dist/core/scenarioModel.js +130 -0
  116. package/dist/core/scenarioModel.js.map +1 -0
  117. package/dist/core/specLayout.d.ts +8 -0
  118. package/dist/core/specLayout.d.ts.map +1 -0
  119. package/dist/core/specLayout.js +36 -0
  120. package/dist/core/specLayout.js.map +1 -0
  121. package/dist/core/types.d.ts +27 -0
  122. package/dist/core/types.d.ts.map +1 -0
  123. package/dist/core/types.js +2 -0
  124. package/dist/core/types.js.map +1 -0
  125. package/dist/core/validate.d.ts +4 -0
  126. package/dist/core/validate.d.ts.map +1 -0
  127. package/dist/core/validate.js +36 -0
  128. package/dist/core/validate.js.map +1 -0
  129. package/dist/core/validators/contracts.d.ts +5 -0
  130. package/dist/core/validators/contracts.d.ts.map +1 -0
  131. package/dist/core/validators/contracts.js +162 -0
  132. package/dist/core/validators/contracts.js.map +1 -0
  133. package/dist/core/validators/delta.d.ts +4 -0
  134. package/dist/core/validators/delta.d.ts.map +1 -0
  135. package/dist/core/validators/delta.js +68 -0
  136. package/dist/core/validators/delta.js.map +1 -0
  137. package/dist/core/validators/ids.d.ts +4 -0
  138. package/dist/core/validators/ids.d.ts.map +1 -0
  139. package/dist/core/validators/ids.js +88 -0
  140. package/dist/core/validators/ids.js.map +1 -0
  141. package/dist/core/validators/scenario.d.ts +5 -0
  142. package/dist/core/validators/scenario.d.ts.map +1 -0
  143. package/dist/core/validators/scenario.js +137 -0
  144. package/dist/core/validators/scenario.js.map +1 -0
  145. package/dist/core/validators/spec.d.ts +5 -0
  146. package/dist/core/validators/spec.d.ts.map +1 -0
  147. package/dist/core/validators/spec.js +94 -0
  148. package/dist/core/validators/spec.js.map +1 -0
  149. package/dist/core/validators/traceability.d.ts +4 -0
  150. package/dist/core/validators/traceability.d.ts.map +1 -0
  151. package/dist/core/validators/traceability.js +180 -0
  152. package/dist/core/validators/traceability.js.map +1 -0
  153. package/dist/core/version.d.ts +2 -0
  154. package/dist/core/version.d.ts.map +1 -0
  155. package/dist/core/version.js +25 -0
  156. package/dist/core/version.js.map +1 -0
  157. package/dist/index.cjs +2 -2
  158. package/dist/index.d.ts +2 -133
  159. package/dist/index.d.ts.map +1 -0
  160. package/dist/index.js +2 -0
  161. package/dist/index.js.map +1 -0
  162. package/dist/index.mjs +2 -2
  163. package/dist/tsconfig.tsbuildinfo +1 -0
  164. package/package.json +1 -1
  165. package/assets/init/root/require/README.md +0 -28
@@ -0,0 +1,2 @@
1
+ export declare function getInitAssetsDir(): string;
2
+ //# sourceMappingURL=assets.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"assets.d.ts","sourceRoot":"","sources":["../../../src/cli/lib/assets.ts"],"names":[],"mappings":"AAIA,wBAAgB,gBAAgB,IAAI,MAAM,CAuBzC"}
@@ -0,0 +1,24 @@
1
+ import { existsSync } from "node:fs";
2
+ import path from "node:path";
3
+ import { fileURLToPath } from "node:url";
4
+ export function getInitAssetsDir() {
5
+ const base = import.meta.url;
6
+ const basePath = base.startsWith("file:") ? fileURLToPath(base) : base;
7
+ const baseDir = path.dirname(basePath);
8
+ // src/cli/lib と dist/cli/lib からの解決を想定する。
9
+ const candidates = [
10
+ path.resolve(baseDir, "../../../assets/init"),
11
+ path.resolve(baseDir, "../../assets/init"),
12
+ ];
13
+ for (const candidate of candidates) {
14
+ if (existsSync(candidate)) {
15
+ return candidate;
16
+ }
17
+ }
18
+ throw new Error([
19
+ "init 用テンプレートが見つかりません。Template assets not found.",
20
+ "確認したパス / Checked paths:",
21
+ ...candidates.map((candidate) => `- ${candidate}`),
22
+ ].join("\n"));
23
+ }
24
+ //# sourceMappingURL=assets.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"assets.js","sourceRoot":"","sources":["../../../src/cli/lib/assets.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,UAAU,gBAAgB;IAC9B,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC;IAC7B,MAAM,QAAQ,GAAG,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;IACvE,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;IACvC,yCAAyC;IACzC,MAAM,UAAU,GAAG;QACjB,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,sBAAsB,CAAC;QAC7C,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,mBAAmB,CAAC;KAC3C,CAAC;IAEF,KAAK,MAAM,SAAS,IAAI,UAAU,EAAE,CAAC;QACnC,IAAI,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;YAC1B,OAAO,SAAS,CAAC;QACnB,CAAC;IACH,CAAC;IAED,MAAM,IAAI,KAAK,CACb;QACE,iDAAiD;QACjD,yBAAyB;QACzB,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,EAAE,CAAC,KAAK,SAAS,EAAE,CAAC;KACnD,CAAC,IAAI,CAAC,IAAI,CAAC,CACb,CAAC;AACJ,CAAC"}
@@ -0,0 +1,5 @@
1
+ import type { FailOn } from "../../core/config.js";
2
+ import type { ValidationResult } from "../../core/types.js";
3
+ export type { FailOn };
4
+ export declare function shouldFail(result: ValidationResult, failOn: FailOn): boolean;
5
+ //# sourceMappingURL=failOn.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"failOn.d.ts","sourceRoot":"","sources":["../../../src/cli/lib/failOn.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AACnD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,qBAAqB,CAAC;AAE5D,YAAY,EAAE,MAAM,EAAE,CAAC;AAEvB,wBAAgB,UAAU,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAQ5E"}
@@ -0,0 +1,10 @@
1
+ export function shouldFail(result, failOn) {
2
+ if (failOn === "never") {
3
+ return false;
4
+ }
5
+ if (failOn === "error") {
6
+ return result.counts.error > 0;
7
+ }
8
+ return result.counts.error + result.counts.warning > 0;
9
+ }
10
+ //# sourceMappingURL=failOn.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"failOn.js","sourceRoot":"","sources":["../../../src/cli/lib/failOn.ts"],"names":[],"mappings":"AAKA,MAAM,UAAU,UAAU,CAAC,MAAwB,EAAE,MAAc;IACjE,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;QACvB,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;QACvB,OAAO,MAAM,CAAC,MAAM,CAAC,KAAK,GAAG,CAAC,CAAC;IACjC,CAAC;IACD,OAAO,MAAM,CAAC,MAAM,CAAC,KAAK,GAAG,MAAM,CAAC,MAAM,CAAC,OAAO,GAAG,CAAC,CAAC;AACzD,CAAC"}
@@ -0,0 +1,11 @@
1
+ export type CopyOptions = {
2
+ force: boolean;
3
+ dryRun: boolean;
4
+ };
5
+ export type CopyResult = {
6
+ copied: string[];
7
+ skipped: string[];
8
+ };
9
+ export declare function copyTemplateTree(sourceRoot: string, destRoot: string, options: CopyOptions): Promise<CopyResult>;
10
+ export declare function copyTemplatePaths(sourceRoot: string, destRoot: string, relativePaths: string[], options: CopyOptions): Promise<CopyResult>;
11
+ //# sourceMappingURL=fs.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fs.d.ts","sourceRoot":"","sources":["../../../src/cli/lib/fs.ts"],"names":[],"mappings":"AAGA,MAAM,MAAM,WAAW,GAAG;IACxB,KAAK,EAAE,OAAO,CAAC;IACf,MAAM,EAAE,OAAO,CAAC;CACjB,CAAC;AAEF,MAAM,MAAM,UAAU,GAAG;IACvB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB,CAAC;AAEF,wBAAsB,gBAAgB,CACpC,UAAU,EAAE,MAAM,EAClB,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,WAAW,GACnB,OAAO,CAAC,UAAU,CAAC,CAGrB;AAED,wBAAsB,iBAAiB,CACrC,UAAU,EAAE,MAAM,EAClB,QAAQ,EAAE,MAAM,EAChB,aAAa,EAAE,MAAM,EAAE,EACvB,OAAO,EAAE,WAAW,GACnB,OAAO,CAAC,UAAU,CAAC,CASrB"}
@@ -0,0 +1,91 @@
1
+ import { access, copyFile, mkdir, readdir } from "node:fs/promises";
2
+ import path from "node:path";
3
+ export async function copyTemplateTree(sourceRoot, destRoot, options) {
4
+ const files = await collectTemplateFiles(sourceRoot);
5
+ return copyFiles(files, sourceRoot, destRoot, options);
6
+ }
7
+ export async function copyTemplatePaths(sourceRoot, destRoot, relativePaths, options) {
8
+ const allFiles = [];
9
+ for (const relPath of relativePaths) {
10
+ const fullPath = path.join(sourceRoot, relPath);
11
+ const files = await collectTemplateFiles(fullPath);
12
+ allFiles.push(...files);
13
+ }
14
+ return copyFiles(allFiles, sourceRoot, destRoot, options);
15
+ }
16
+ async function copyFiles(files, sourceRoot, destRoot, options) {
17
+ const copied = [];
18
+ const skipped = [];
19
+ const conflicts = [];
20
+ if (!options.force) {
21
+ for (const file of files) {
22
+ const relative = path.relative(sourceRoot, file);
23
+ const dest = path.join(destRoot, relative);
24
+ if (!(await shouldWrite(dest, options.force))) {
25
+ conflicts.push(dest);
26
+ }
27
+ }
28
+ if (conflicts.length > 0) {
29
+ throw new Error(formatConflictMessage(conflicts));
30
+ }
31
+ }
32
+ for (const file of files) {
33
+ const relative = path.relative(sourceRoot, file);
34
+ const dest = path.join(destRoot, relative);
35
+ if (!(await shouldWrite(dest, options.force))) {
36
+ skipped.push(dest);
37
+ continue;
38
+ }
39
+ if (!options.dryRun) {
40
+ await mkdir(path.dirname(dest), { recursive: true });
41
+ await copyFile(file, dest);
42
+ }
43
+ copied.push(dest);
44
+ }
45
+ return { copied, skipped };
46
+ }
47
+ function formatConflictMessage(conflicts) {
48
+ return [
49
+ "既存ファイルと衝突しました。安全のため停止します。",
50
+ "",
51
+ "衝突ファイル:",
52
+ ...conflicts.map((conflict) => `- ${conflict}`),
53
+ "",
54
+ "上書きして続行する場合は --force を付けて再実行してください。",
55
+ ].join("\n");
56
+ }
57
+ async function collectTemplateFiles(root) {
58
+ const entries = [];
59
+ if (!(await exists(root))) {
60
+ return entries;
61
+ }
62
+ const items = await readdir(root, { withFileTypes: true });
63
+ for (const item of items) {
64
+ const fullPath = path.join(root, item.name);
65
+ if (item.isDirectory()) {
66
+ const nested = await collectTemplateFiles(fullPath);
67
+ entries.push(...nested);
68
+ continue;
69
+ }
70
+ if (item.isFile()) {
71
+ entries.push(fullPath);
72
+ }
73
+ }
74
+ return entries;
75
+ }
76
+ async function shouldWrite(target, force) {
77
+ if (force) {
78
+ return true;
79
+ }
80
+ return !(await exists(target));
81
+ }
82
+ async function exists(target) {
83
+ try {
84
+ await access(target);
85
+ return true;
86
+ }
87
+ catch {
88
+ return false;
89
+ }
90
+ }
91
+ //# sourceMappingURL=fs.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fs.js","sourceRoot":"","sources":["../../../src/cli/lib/fs.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,kBAAkB,CAAC;AACpE,OAAO,IAAI,MAAM,WAAW,CAAC;AAY7B,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACpC,UAAkB,EAClB,QAAgB,EAChB,OAAoB;IAEpB,MAAM,KAAK,GAAG,MAAM,oBAAoB,CAAC,UAAU,CAAC,CAAC;IACrD,OAAO,SAAS,CAAC,KAAK,EAAE,UAAU,EAAE,QAAQ,EAAE,OAAO,CAAC,CAAC;AACzD,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,iBAAiB,CACrC,UAAkB,EAClB,QAAgB,EAChB,aAAuB,EACvB,OAAoB;IAEpB,MAAM,QAAQ,GAAa,EAAE,CAAC;IAC9B,KAAK,MAAM,OAAO,IAAI,aAAa,EAAE,CAAC;QACpC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;QAChD,MAAM,KAAK,GAAG,MAAM,oBAAoB,CAAC,QAAQ,CAAC,CAAC;QACnD,QAAQ,CAAC,IAAI,CAAC,GAAG,KAAK,CAAC,CAAC;IAC1B,CAAC;IAED,OAAO,SAAS,CAAC,QAAQ,EAAE,UAAU,EAAE,QAAQ,EAAE,OAAO,CAAC,CAAC;AAC5D,CAAC;AAED,KAAK,UAAU,SAAS,CACtB,KAAe,EACf,UAAkB,EAClB,QAAgB,EAChB,OAAoB;IAEpB,MAAM,MAAM,GAAa,EAAE,CAAC;IAC5B,MAAM,OAAO,GAAa,EAAE,CAAC;IAC7B,MAAM,SAAS,GAAa,EAAE,CAAC;IAE/B,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC;QACnB,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;YACzB,MAAM,QAAQ,GAAG,IAAI,CAAC,QAAQ,CAAC,UAAU,EAAE,IAAI,CAAC,CAAC;YACjD,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;YAC3C,IAAI,CAAC,CAAC,MAAM,WAAW,CAAC,IAAI,EAAE,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC;gBAC9C,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACvB,CAAC;QACH,CAAC;QAED,IAAI,SAAS,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACzB,MAAM,IAAI,KAAK,CAAC,qBAAqB,CAAC,SAAS,CAAC,CAAC,CAAC;QACpD,CAAC;IACH,CAAC;IAED,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,QAAQ,GAAG,IAAI,CAAC,QAAQ,CAAC,UAAU,EAAE,IAAI,CAAC,CAAC;QACjD,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;QAE3C,IAAI,CAAC,CAAC,MAAM,WAAW,CAAC,IAAI,EAAE,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC;YAC9C,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACnB,SAAS;QACX,CAAC;QAED,IAAI,CAAC,OAAO,CAAC,MAAM,EAAE,CAAC;YACpB,MAAM,KAAK,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;YACrD,MAAM,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;QAC7B,CAAC;QACD,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACpB,CAAC;IAED,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,CAAC;AAC7B,CAAC;AAED,SAAS,qBAAqB,CAAC,SAAmB;IAChD,OAAO;QACL,2BAA2B;QAC3B,EAAE;QACF,SAAS;QACT,GAAG,SAAS,CAAC,GAAG,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC,KAAK,QAAQ,EAAE,CAAC;QAC/C,EAAE;QACF,qCAAqC;KACtC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AACf,CAAC;AAED,KAAK,UAAU,oBAAoB,CAAC,IAAY;IAC9C,MAAM,OAAO,GAAa,EAAE,CAAC;IAC7B,IAAI,CAAC,CAAC,MAAM,MAAM,CAAC,IAAI,CAAC,CAAC,EAAE,CAAC;QAC1B,OAAO,OAAO,CAAC;IACjB,CAAC;IAED,MAAM,KAAK,GAAG,MAAM,OAAO,CAAC,IAAI,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAC3D,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC;QAC5C,IAAI,IAAI,CAAC,WAAW,EAAE,EAAE,CAAC;YACvB,MAAM,MAAM,GAAG,MAAM,oBAAoB,CAAC,QAAQ,CAAC,CAAC;YACpD,OAAO,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,CAAC;YACxB,SAAS;QACX,CAAC;QACD,IAAI,IAAI,CAAC,MAAM,EAAE,EAAE,CAAC;YAClB,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACzB,CAAC;IACH,CAAC;IAED,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,KAAK,UAAU,WAAW,CAAC,MAAc,EAAE,KAAc;IACvD,IAAI,KAAK,EAAE,CAAC;QACV,OAAO,IAAI,CAAC;IACd,CAAC;IACD,OAAO,CAAC,CAAC,MAAM,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC;AACjC,CAAC;AAED,KAAK,UAAU,MAAM,CAAC,MAAc;IAClC,IAAI,CAAC;QACH,MAAM,MAAM,CAAC,MAAM,CAAC,CAAC;QACrB,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC"}
@@ -0,0 +1,4 @@
1
+ export declare function info(message: string): void;
2
+ export declare function warn(message: string): void;
3
+ export declare function error(message: string): void;
4
+ //# sourceMappingURL=logger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../../src/cli/lib/logger.ts"],"names":[],"mappings":"AAAA,wBAAgB,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAE1C;AAED,wBAAgB,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAE1C;AAED,wBAAgB,KAAK,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAE3C"}
@@ -0,0 +1,10 @@
1
+ export function info(message) {
2
+ process.stdout.write(`${message}\n`);
3
+ }
4
+ export function warn(message) {
5
+ process.stdout.write(`${message}\n`);
6
+ }
7
+ export function error(message) {
8
+ process.stderr.write(`${message}\n`);
9
+ }
10
+ //# sourceMappingURL=logger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../../../src/cli/lib/logger.ts"],"names":[],"mappings":"AAAA,MAAM,UAAU,IAAI,CAAC,OAAe;IAClC,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,OAAO,IAAI,CAAC,CAAC;AACvC,CAAC;AAED,MAAM,UAAU,IAAI,CAAC,OAAe;IAClC,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,OAAO,IAAI,CAAC,CAAC;AACvC,CAAC;AAED,MAAM,UAAU,KAAK,CAAC,OAAe;IACnC,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,OAAO,IAAI,CAAC,CAAC;AACvC,CAAC"}
@@ -0,0 +1,2 @@
1
+ export declare function run(argv: string[], cwd: string): Promise<void>;
2
+ //# sourceMappingURL=main.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"main.d.ts","sourceRoot":"","sources":["../../src/cli/main.ts"],"names":[],"mappings":"AAMA,wBAAsB,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAuCpE"}
@@ -0,0 +1,66 @@
1
+ import { runInit } from "./commands/init.js";
2
+ import { runReport } from "./commands/report.js";
3
+ import { runValidate } from "./commands/validate.js";
4
+ import { parseArgs } from "./lib/args.js";
5
+ import { error, info } from "./lib/logger.js";
6
+ export async function run(argv, cwd) {
7
+ const { command, options } = parseArgs(argv, cwd);
8
+ if (!command || options.help) {
9
+ info(usage());
10
+ return;
11
+ }
12
+ switch (command) {
13
+ case "init":
14
+ await runInit({
15
+ dir: options.dir,
16
+ force: options.force,
17
+ dryRun: options.dryRun,
18
+ yes: options.yes,
19
+ });
20
+ return;
21
+ case "validate":
22
+ process.exitCode = await runValidate({
23
+ root: options.root,
24
+ strict: options.strict,
25
+ format: options.validateFormat,
26
+ ...(options.failOn !== undefined ? { failOn: options.failOn } : {}),
27
+ });
28
+ return;
29
+ case "report":
30
+ await runReport({
31
+ root: options.root,
32
+ format: options.reportFormat,
33
+ ...(options.reportOut !== undefined
34
+ ? { outPath: options.reportOut }
35
+ : {}),
36
+ });
37
+ return;
38
+ default:
39
+ error(`Unknown command: ${command}`);
40
+ info(usage());
41
+ return;
42
+ }
43
+ }
44
+ function usage() {
45
+ return `qfai <command> [options]
46
+
47
+ Commands:
48
+ init テンプレを生成
49
+ validate 仕様/契約/参照の検査
50
+ report 検証結果と集計を出力
51
+
52
+ Options:
53
+ --root <path> 対象ディレクトリ
54
+ --dir <path> init の出力先
55
+ --force 既存ファイルを上書き
56
+ --yes init: 予約フラグ(現状は非対話のため挙動差なし。将来の対話導入時に自動Yes)
57
+ --dry-run 変更を行わず表示のみ
58
+ --format <text|github> validate の出力形式
59
+ --format <md|json> report の出力形式
60
+ --strict validate: warning 以上で exit 1
61
+ --fail-on <error|warning|never> validate: 失敗条件
62
+ --out <path> report: 出力先
63
+ -h, --help ヘルプ表示
64
+ `;
65
+ }
66
+ //# sourceMappingURL=main.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"main.js","sourceRoot":"","sources":["../../src/cli/main.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAC7C,OAAO,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AACjD,OAAO,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAC;AACrD,OAAO,EAAE,SAAS,EAAE,MAAM,eAAe,CAAC;AAC1C,OAAO,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAC;AAE9C,MAAM,CAAC,KAAK,UAAU,GAAG,CAAC,IAAc,EAAE,GAAW;IACnD,MAAM,EAAE,OAAO,EAAE,OAAO,EAAE,GAAG,SAAS,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;IAElD,IAAI,CAAC,OAAO,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC;QAC7B,IAAI,CAAC,KAAK,EAAE,CAAC,CAAC;QACd,OAAO;IACT,CAAC;IAED,QAAQ,OAAO,EAAE,CAAC;QAChB,KAAK,MAAM;YACT,MAAM,OAAO,CAAC;gBACZ,GAAG,EAAE,OAAO,CAAC,GAAG;gBAChB,KAAK,EAAE,OAAO,CAAC,KAAK;gBACpB,MAAM,EAAE,OAAO,CAAC,MAAM;gBACtB,GAAG,EAAE,OAAO,CAAC,GAAG;aACjB,CAAC,CAAC;YACH,OAAO;QACT,KAAK,UAAU;YACb,OAAO,CAAC,QAAQ,GAAG,MAAM,WAAW,CAAC;gBACnC,IAAI,EAAE,OAAO,CAAC,IAAI;gBAClB,MAAM,EAAE,OAAO,CAAC,MAAM;gBACtB,MAAM,EAAE,OAAO,CAAC,cAAc;gBAC9B,GAAG,CAAC,OAAO,CAAC,MAAM,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;aACpE,CAAC,CAAC;YACH,OAAO;QACT,KAAK,QAAQ;YACX,MAAM,SAAS,CAAC;gBACd,IAAI,EAAE,OAAO,CAAC,IAAI;gBAClB,MAAM,EAAE,OAAO,CAAC,YAAY;gBAC5B,GAAG,CAAC,OAAO,CAAC,SAAS,KAAK,SAAS;oBACjC,CAAC,CAAC,EAAE,OAAO,EAAE,OAAO,CAAC,SAAS,EAAE;oBAChC,CAAC,CAAC,EAAE,CAAC;aACR,CAAC,CAAC;YACH,OAAO;QACT;YACE,KAAK,CAAC,oBAAoB,OAAO,EAAE,CAAC,CAAC;YACrC,IAAI,CAAC,KAAK,EAAE,CAAC,CAAC;YACd,OAAO;IACX,CAAC;AACH,CAAC;AAED,SAAS,KAAK;IACZ,OAAO;;;;;;;;;;;;;;;;;;;CAmBR,CAAC;AACF,CAAC"}
@@ -0,0 +1,44 @@
1
+ import type { Issue } from "./types.js";
2
+ export type FailOn = "never" | "warning" | "error";
3
+ export type OutputFormat = "text" | "github";
4
+ export type TraceabilitySeverity = "warning" | "error";
5
+ export type QfaiPaths = {
6
+ contractsDir: string;
7
+ specsDir: string;
8
+ rulesDir: string;
9
+ outDir: string;
10
+ promptsDir: string;
11
+ srcDir: string;
12
+ testsDir: string;
13
+ };
14
+ export type QfaiValidationConfig = {
15
+ failOn: FailOn;
16
+ require: {
17
+ specSections: string[];
18
+ };
19
+ traceability: {
20
+ brMustHaveSc: boolean;
21
+ scMustTouchContracts: boolean;
22
+ allowOrphanContracts: boolean;
23
+ unknownContractIdSeverity: TraceabilitySeverity;
24
+ };
25
+ };
26
+ export type QfaiOutputConfig = {
27
+ validateJsonPath: string;
28
+ };
29
+ export type QfaiConfig = {
30
+ paths: QfaiPaths;
31
+ validation: QfaiValidationConfig;
32
+ output: QfaiOutputConfig;
33
+ };
34
+ export type ConfigPathKey = keyof QfaiPaths;
35
+ export type ConfigLoadResult = {
36
+ config: QfaiConfig;
37
+ issues: Issue[];
38
+ configPath: string;
39
+ };
40
+ export declare const defaultConfig: QfaiConfig;
41
+ export declare function getConfigPath(root: string): string;
42
+ export declare function loadConfig(root: string): Promise<ConfigLoadResult>;
43
+ export declare function resolvePath(root: string, config: QfaiConfig, key: ConfigPathKey): string;
44
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/core/config.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAExC,MAAM,MAAM,MAAM,GAAG,OAAO,GAAG,SAAS,GAAG,OAAO,CAAC;AACnD,MAAM,MAAM,YAAY,GAAG,MAAM,GAAG,QAAQ,CAAC;AAC7C,MAAM,MAAM,oBAAoB,GAAG,SAAS,GAAG,OAAO,CAAC;AAEvD,MAAM,MAAM,SAAS,GAAG;IACtB,YAAY,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;IACf,UAAU,EAAE,MAAM,CAAC;IACnB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,MAAM,MAAM,oBAAoB,GAAG;IACjC,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE;QACP,YAAY,EAAE,MAAM,EAAE,CAAC;KACxB,CAAC;IACF,YAAY,EAAE;QACZ,YAAY,EAAE,OAAO,CAAC;QACtB,oBAAoB,EAAE,OAAO,CAAC;QAC9B,oBAAoB,EAAE,OAAO,CAAC;QAC9B,yBAAyB,EAAE,oBAAoB,CAAC;KACjD,CAAC;CACH,CAAC;AAEF,MAAM,MAAM,gBAAgB,GAAG;IAC7B,gBAAgB,EAAE,MAAM,CAAC;CAC1B,CAAC;AAEF,MAAM,MAAM,UAAU,GAAG;IACvB,KAAK,EAAE,SAAS,CAAC;IACjB,UAAU,EAAE,oBAAoB,CAAC;IACjC,MAAM,EAAE,gBAAgB,CAAC;CAC1B,CAAC;AAEF,MAAM,MAAM,aAAa,GAAG,MAAM,SAAS,CAAC;AAE5C,MAAM,MAAM,gBAAgB,GAAG;IAC7B,MAAM,EAAE,UAAU,CAAC;IACnB,MAAM,EAAE,KAAK,EAAE,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,eAAO,MAAM,aAAa,EAAE,UAiC3B,CAAC;AAEF,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAElD;AAED,wBAAsB,UAAU,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAkBxE;AAED,wBAAgB,WAAW,CACzB,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,UAAU,EAClB,GAAG,EAAE,aAAa,GACjB,MAAM,CAER"}
@@ -0,0 +1,218 @@
1
+ import { readFile } from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { parse as parseYaml } from "yaml";
4
+ export const defaultConfig = {
5
+ paths: {
6
+ contractsDir: ".qfai/contracts",
7
+ specsDir: ".qfai/specs",
8
+ rulesDir: ".qfai/rules",
9
+ outDir: ".qfai/out",
10
+ promptsDir: ".qfai/prompts",
11
+ srcDir: "src",
12
+ testsDir: "tests",
13
+ },
14
+ validation: {
15
+ failOn: "error",
16
+ require: {
17
+ specSections: [
18
+ "背景",
19
+ "スコープ",
20
+ "非ゴール",
21
+ "用語",
22
+ "前提",
23
+ "決定事項",
24
+ "業務ルール",
25
+ ],
26
+ },
27
+ traceability: {
28
+ brMustHaveSc: true,
29
+ scMustTouchContracts: true,
30
+ allowOrphanContracts: false,
31
+ unknownContractIdSeverity: "error",
32
+ },
33
+ },
34
+ output: {
35
+ validateJsonPath: ".qfai/out/validate.json",
36
+ },
37
+ };
38
+ export function getConfigPath(root) {
39
+ return path.join(root, "qfai.config.yaml");
40
+ }
41
+ export async function loadConfig(root) {
42
+ const configPath = getConfigPath(root);
43
+ const issues = [];
44
+ let parsed;
45
+ try {
46
+ const raw = await readFile(configPath, "utf-8");
47
+ parsed = parseYaml(raw);
48
+ }
49
+ catch (error) {
50
+ if (isMissingFile(error)) {
51
+ return { config: defaultConfig, issues, configPath };
52
+ }
53
+ issues.push(configIssue(configPath, formatError(error)));
54
+ return { config: defaultConfig, issues, configPath };
55
+ }
56
+ const normalized = normalizeConfig(parsed, configPath, issues);
57
+ return { config: normalized, issues, configPath };
58
+ }
59
+ export function resolvePath(root, config, key) {
60
+ return path.resolve(root, config.paths[key]);
61
+ }
62
+ function normalizeConfig(raw, configPath, issues) {
63
+ if (!isRecord(raw)) {
64
+ issues.push(configIssue(configPath, "設定ファイルの形式が不正です。"));
65
+ return defaultConfig;
66
+ }
67
+ return {
68
+ paths: normalizePaths(raw.paths, configPath, issues),
69
+ validation: normalizeValidation(raw.validation, configPath, issues),
70
+ output: normalizeOutput(raw.output, configPath, issues),
71
+ };
72
+ }
73
+ function normalizePaths(raw, configPath, issues) {
74
+ const base = defaultConfig.paths;
75
+ if (!raw) {
76
+ return base;
77
+ }
78
+ if (!isRecord(raw)) {
79
+ issues.push(configIssue(configPath, "paths はオブジェクトである必要があります。"));
80
+ return base;
81
+ }
82
+ return {
83
+ contractsDir: readString(raw.contractsDir, base.contractsDir, "paths.contractsDir", configPath, issues),
84
+ specsDir: readString(raw.specsDir, base.specsDir, "paths.specsDir", configPath, issues),
85
+ rulesDir: readString(raw.rulesDir, base.rulesDir, "paths.rulesDir", configPath, issues),
86
+ outDir: readString(raw.outDir, base.outDir, "paths.outDir", configPath, issues),
87
+ promptsDir: readString(raw.promptsDir, base.promptsDir, "paths.promptsDir", configPath, issues),
88
+ srcDir: readString(raw.srcDir, base.srcDir, "paths.srcDir", configPath, issues),
89
+ testsDir: readString(raw.testsDir, base.testsDir, "paths.testsDir", configPath, issues),
90
+ };
91
+ }
92
+ function normalizeValidation(raw, configPath, issues) {
93
+ const base = defaultConfig.validation;
94
+ if (!raw) {
95
+ return base;
96
+ }
97
+ if (!isRecord(raw)) {
98
+ issues.push(configIssue(configPath, "validation はオブジェクトである必要があります。"));
99
+ return base;
100
+ }
101
+ let requireRaw;
102
+ if (raw.require === undefined) {
103
+ requireRaw = undefined;
104
+ }
105
+ else if (isRecord(raw.require)) {
106
+ requireRaw = raw.require;
107
+ }
108
+ else {
109
+ issues.push(configIssue(configPath, "validation.require はオブジェクトである必要があります。"));
110
+ requireRaw = undefined;
111
+ }
112
+ let traceabilityRaw;
113
+ if (raw.traceability === undefined) {
114
+ traceabilityRaw = undefined;
115
+ }
116
+ else if (isRecord(raw.traceability)) {
117
+ traceabilityRaw = raw.traceability;
118
+ }
119
+ else {
120
+ issues.push(configIssue(configPath, "validation.traceability はオブジェクトである必要があります。"));
121
+ traceabilityRaw = undefined;
122
+ }
123
+ return {
124
+ failOn: readFailOn(raw.failOn, base.failOn, "validation.failOn", configPath, issues),
125
+ require: {
126
+ specSections: readStringArray(requireRaw?.specSections, base.require.specSections, "validation.require.specSections", configPath, issues),
127
+ },
128
+ traceability: {
129
+ brMustHaveSc: readBoolean(traceabilityRaw?.brMustHaveSc, base.traceability.brMustHaveSc, "validation.traceability.brMustHaveSc", configPath, issues),
130
+ scMustTouchContracts: readBoolean(traceabilityRaw?.scMustTouchContracts, base.traceability.scMustTouchContracts, "validation.traceability.scMustTouchContracts", configPath, issues),
131
+ allowOrphanContracts: readBoolean(traceabilityRaw?.allowOrphanContracts, base.traceability.allowOrphanContracts, "validation.traceability.allowOrphanContracts", configPath, issues),
132
+ unknownContractIdSeverity: readTraceabilitySeverity(traceabilityRaw?.unknownContractIdSeverity, base.traceability.unknownContractIdSeverity, "validation.traceability.unknownContractIdSeverity", configPath, issues),
133
+ },
134
+ };
135
+ }
136
+ function normalizeOutput(raw, configPath, issues) {
137
+ const base = defaultConfig.output;
138
+ if (!raw) {
139
+ return base;
140
+ }
141
+ if (!isRecord(raw)) {
142
+ issues.push(configIssue(configPath, "output はオブジェクトである必要があります。"));
143
+ return base;
144
+ }
145
+ return {
146
+ validateJsonPath: readString(raw.validateJsonPath, base.validateJsonPath, "output.validateJsonPath", configPath, issues),
147
+ };
148
+ }
149
+ function readString(value, fallback, label, configPath, issues) {
150
+ if (typeof value === "string" && value.trim().length > 0) {
151
+ return value;
152
+ }
153
+ if (value !== undefined) {
154
+ issues.push(configIssue(configPath, `${label} は文字列である必要があります。`));
155
+ }
156
+ return fallback;
157
+ }
158
+ function readStringArray(value, fallback, label, configPath, issues) {
159
+ if (Array.isArray(value) && value.every((item) => typeof item === "string")) {
160
+ return value;
161
+ }
162
+ if (value !== undefined) {
163
+ issues.push(configIssue(configPath, `${label} は文字列配列である必要があります。`));
164
+ }
165
+ return fallback;
166
+ }
167
+ function readBoolean(value, fallback, label, configPath, issues) {
168
+ if (typeof value === "boolean") {
169
+ return value;
170
+ }
171
+ if (value !== undefined) {
172
+ issues.push(configIssue(configPath, `${label} は真偽値である必要があります。`));
173
+ }
174
+ return fallback;
175
+ }
176
+ function readFailOn(value, fallback, label, configPath, issues) {
177
+ if (value === "never" || value === "warning" || value === "error") {
178
+ return value;
179
+ }
180
+ if (value !== undefined) {
181
+ issues.push(configIssue(configPath, `${label} は never|warning|error のいずれかである必要があります。`));
182
+ }
183
+ return fallback;
184
+ }
185
+ function readTraceabilitySeverity(value, fallback, label, configPath, issues) {
186
+ if (value === "warning" || value === "error") {
187
+ return value;
188
+ }
189
+ if (value !== undefined) {
190
+ issues.push(configIssue(configPath, `${label} は warning|error のいずれかである必要があります。`));
191
+ }
192
+ return fallback;
193
+ }
194
+ function configIssue(file, message) {
195
+ return {
196
+ code: "QFAI_CONFIG_INVALID",
197
+ severity: "error",
198
+ message,
199
+ file,
200
+ rule: "config.invalid",
201
+ };
202
+ }
203
+ function isMissingFile(error) {
204
+ if (error && typeof error === "object" && "code" in error) {
205
+ return error.code === "ENOENT";
206
+ }
207
+ return false;
208
+ }
209
+ function formatError(error) {
210
+ if (error instanceof Error) {
211
+ return error.message;
212
+ }
213
+ return String(error);
214
+ }
215
+ function isRecord(value) {
216
+ return value !== null && typeof value === "object" && !Array.isArray(value);
217
+ }
218
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/core/config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,IAAI,MAAM,WAAW,CAAC;AAE7B,OAAO,EAAE,KAAK,IAAI,SAAS,EAAE,MAAM,MAAM,CAAC;AAiD1C,MAAM,CAAC,MAAM,aAAa,GAAe;IACvC,KAAK,EAAE;QACL,YAAY,EAAE,iBAAiB;QAC/B,QAAQ,EAAE,aAAa;QACvB,QAAQ,EAAE,aAAa;QACvB,MAAM,EAAE,WAAW;QACnB,UAAU,EAAE,eAAe;QAC3B,MAAM,EAAE,KAAK;QACb,QAAQ,EAAE,OAAO;KAClB;IACD,UAAU,EAAE;QACV,MAAM,EAAE,OAAO;QACf,OAAO,EAAE;YACP,YAAY,EAAE;gBACZ,IAAI;gBACJ,MAAM;gBACN,MAAM;gBACN,IAAI;gBACJ,IAAI;gBACJ,MAAM;gBACN,OAAO;aACR;SACF;QACD,YAAY,EAAE;YACZ,YAAY,EAAE,IAAI;YAClB,oBAAoB,EAAE,IAAI;YAC1B,oBAAoB,EAAE,KAAK;YAC3B,yBAAyB,EAAE,OAAO;SACnC;KACF;IACD,MAAM,EAAE;QACN,gBAAgB,EAAE,yBAAyB;KAC5C;CACF,CAAC;AAEF,MAAM,UAAU,aAAa,CAAC,IAAY;IACxC,OAAO,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,kBAAkB,CAAC,CAAC;AAC7C,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,UAAU,CAAC,IAAY;IAC3C,MAAM,UAAU,GAAG,aAAa,CAAC,IAAI,CAAC,CAAC;IACvC,MAAM,MAAM,GAAY,EAAE,CAAC;IAE3B,IAAI,MAAe,CAAC;IACpB,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;QAChD,MAAM,GAAG,SAAS,CAAC,GAAG,CAAC,CAAC;IAC1B,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,aAAa,CAAC,KAAK,CAAC,EAAE,CAAC;YACzB,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,UAAU,EAAE,CAAC;QACvD,CAAC;QACD,MAAM,CAAC,IAAI,CAAC,WAAW,CAAC,UAAU,EAAE,WAAW,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;QACzD,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,UAAU,EAAE,CAAC;IACvD,CAAC;IAED,MAAM,UAAU,GAAG,eAAe,CAAC,MAAM,EAAE,UAAU,EAAE,MAAM,CAAC,CAAC;IAC/D,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,EAAE,UAAU,EAAE,CAAC;AACpD,CAAC;AAED,MAAM,UAAU,WAAW,CACzB,IAAY,EACZ,MAAkB,EAClB,GAAkB;IAElB,OAAO,IAAI,CAAC,OAAO,CAAC,IAAI,EAAE,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC;AAC/C,CAAC;AAED,SAAS,eAAe,CACtB,GAAY,EACZ,UAAkB,EAClB,MAAe;IAEf,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACnB,MAAM,CAAC,IAAI,CAAC,WAAW,CAAC,UAAU,EAAE,iBAAiB,CAAC,CAAC,CAAC;QACxD,OAAO,aAAa,CAAC;IACvB,CAAC;IAED,OAAO;QACL,KAAK,EAAE,cAAc,CAAC,GAAG,CAAC,KAAK,EAAE,UAAU,EAAE,MAAM,CAAC;QACpD,UAAU,EAAE,mBAAmB,CAAC,GAAG,CAAC,UAAU,EAAE,UAAU,EAAE,MAAM,CAAC;QACnE,MAAM,EAAE,eAAe,CAAC,GAAG,CAAC,MAAM,EAAE,UAAU,EAAE,MAAM,CAAC;KACxD,CAAC;AACJ,CAAC;AAED,SAAS,cAAc,CACrB,GAAY,EACZ,UAAkB,EAClB,MAAe;IAEf,MAAM,IAAI,GAAG,aAAa,CAAC,KAAK,CAAC;IACjC,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,OAAO,IAAI,CAAC;IACd,CAAC;IACD,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACnB,MAAM,CAAC,IAAI,CACT,WAAW,CAAC,UAAU,EAAE,0BAA0B,CAAC,CACpD,CAAC;QACF,OAAO,IAAI,CAAC;IACd,CAAC;IAED,OAAO;QACL,YAAY,EAAE,UAAU,CACtB,GAAG,CAAC,YAAY,EAChB,IAAI,CAAC,YAAY,EACjB,oBAAoB,EACpB,UAAU,EACV,MAAM,CACP;QACD,QAAQ,EAAE,UAAU,CAClB,GAAG,CAAC,QAAQ,EACZ,IAAI,CAAC,QAAQ,EACb,gBAAgB,EAChB,UAAU,EACV,MAAM,CACP;QACD,QAAQ,EAAE,UAAU,CAClB,GAAG,CAAC,QAAQ,EACZ,IAAI,CAAC,QAAQ,EACb,gBAAgB,EAChB,UAAU,EACV,MAAM,CACP;QACD,MAAM,EAAE,UAAU,CAChB,GAAG,CAAC,MAAM,EACV,IAAI,CAAC,MAAM,EACX,cAAc,EACd,UAAU,EACV,MAAM,CACP;QACD,UAAU,EAAE,UAAU,CACpB,GAAG,CAAC,UAAU,EACd,IAAI,CAAC,UAAU,EACf,kBAAkB,EAClB,UAAU,EACV,MAAM,CACP;QACD,MAAM,EAAE,UAAU,CAChB,GAAG,CAAC,MAAM,EACV,IAAI,CAAC,MAAM,EACX,cAAc,EACd,UAAU,EACV,MAAM,CACP;QACD,QAAQ,EAAE,UAAU,CAClB,GAAG,CAAC,QAAQ,EACZ,IAAI,CAAC,QAAQ,EACb,gBAAgB,EAChB,UAAU,EACV,MAAM,CACP;KACF,CAAC;AACJ,CAAC;AAED,SAAS,mBAAmB,CAC1B,GAAY,EACZ,UAAkB,EAClB,MAAe;IAEf,MAAM,IAAI,GAAG,aAAa,CAAC,UAAU,CAAC;IACtC,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,OAAO,IAAI,CAAC;IACd,CAAC;IACD,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACnB,MAAM,CAAC,IAAI,CACT,WAAW,CACT,UAAU,EACV,+BAA+B,CAChC,CACF,CAAC;QACF,OAAO,IAAI,CAAC;IACd,CAAC;IAED,IAAI,UAA+C,CAAC;IACpD,IAAI,GAAG,CAAC,OAAO,KAAK,SAAS,EAAE,CAAC;QAC9B,UAAU,GAAG,SAAS,CAAC;IACzB,CAAC;SAAM,IAAI,QAAQ,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,CAAC;QACjC,UAAU,GAAG,GAAG,CAAC,OAAO,CAAC;IAC3B,CAAC;SAAM,CAAC;QACN,MAAM,CAAC,IAAI,CACT,WAAW,CACT,UAAU,EACV,uCAAuC,CACxC,CACF,CAAC;QACF,UAAU,GAAG,SAAS,CAAC;IACzB,CAAC;IAED,IAAI,eAAoD,CAAC;IACzD,IAAI,GAAG,CAAC,YAAY,KAAK,SAAS,EAAE,CAAC;QACnC,eAAe,GAAG,SAAS,CAAC;IAC9B,CAAC;SAAM,IAAI,QAAQ,CAAC,GAAG,CAAC,YAAY,CAAC,EAAE,CAAC;QACtC,eAAe,GAAG,GAAG,CAAC,YAAY,CAAC;IACrC,CAAC;SAAM,CAAC;QACN,MAAM,CAAC,IAAI,CACT,WAAW,CACT,UAAU,EACV,4CAA4C,CAC7C,CACF,CAAC;QACF,eAAe,GAAG,SAAS,CAAC;IAC9B,CAAC;IAED,OAAO;QACL,MAAM,EAAE,UAAU,CAChB,GAAG,CAAC,MAAM,EACV,IAAI,CAAC,MAAM,EACX,mBAAmB,EACnB,UAAU,EACV,MAAM,CACP;QACD,OAAO,EAAE;YACP,YAAY,EAAE,eAAe,CAC3B,UAAU,EAAE,YAAY,EACxB,IAAI,CAAC,OAAO,CAAC,YAAY,EACzB,iCAAiC,EACjC,UAAU,EACV,MAAM,CACP;SACF;QACD,YAAY,EAAE;YACZ,YAAY,EAAE,WAAW,CACvB,eAAe,EAAE,YAAY,EAC7B,IAAI,CAAC,YAAY,CAAC,YAAY,EAC9B,sCAAsC,EACtC,UAAU,EACV,MAAM,CACP;YACD,oBAAoB,EAAE,WAAW,CAC/B,eAAe,EAAE,oBAAoB,EACrC,IAAI,CAAC,YAAY,CAAC,oBAAoB,EACtC,8CAA8C,EAC9C,UAAU,EACV,MAAM,CACP;YACD,oBAAoB,EAAE,WAAW,CAC/B,eAAe,EAAE,oBAAoB,EACrC,IAAI,CAAC,YAAY,CAAC,oBAAoB,EACtC,8CAA8C,EAC9C,UAAU,EACV,MAAM,CACP;YACD,yBAAyB,EAAE,wBAAwB,CACjD,eAAe,EAAE,yBAAyB,EAC1C,IAAI,CAAC,YAAY,CAAC,yBAAyB,EAC3C,mDAAmD,EACnD,UAAU,EACV,MAAM,CACP;SACF;KACF,CAAC;AACJ,CAAC;AAED,SAAS,eAAe,CACtB,GAAY,EACZ,UAAkB,EAClB,MAAe;IAEf,MAAM,IAAI,GAAG,aAAa,CAAC,MAAM,CAAC;IAClC,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,OAAO,IAAI,CAAC;IACd,CAAC;IACD,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACnB,MAAM,CAAC,IAAI,CACT,WAAW,CAAC,UAAU,EAAE,2BAA2B,CAAC,CACrD,CAAC;QACF,OAAO,IAAI,CAAC;IACd,CAAC;IAED,OAAO;QACL,gBAAgB,EAAE,UAAU,CAC1B,GAAG,CAAC,gBAAgB,EACpB,IAAI,CAAC,gBAAgB,EACrB,yBAAyB,EACzB,UAAU,EACV,MAAM,CACP;KACF,CAAC;AACJ,CAAC;AAED,SAAS,UAAU,CACjB,KAAc,EACd,QAAgB,EAChB,KAAa,EACb,UAAkB,EAClB,MAAe;IAEf,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACzD,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QACxB,MAAM,CAAC,IAAI,CACT,WAAW,CAAC,UAAU,EAAE,GAAG,KAAK,kBAAkB,CAAC,CACpD,CAAC;IACJ,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,eAAe,CACtB,KAAc,EACd,QAAkB,EAClB,KAAa,EACb,UAAkB,EAClB,MAAe;IAEf,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,OAAO,IAAI,KAAK,QAAQ,CAAC,EAAE,CAAC;QAC5E,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QACxB,MAAM,CAAC,IAAI,CACT,WAAW,CAAC,UAAU,EAAE,GAAG,KAAK,oBAAoB,CAAC,CACtD,CAAC;IACJ,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,WAAW,CAClB,KAAc,EACd,QAAiB,EACjB,KAAa,EACb,UAAkB,EAClB,MAAe;IAEf,IAAI,OAAO,KAAK,KAAK,SAAS,EAAE,CAAC;QAC/B,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QACxB,MAAM,CAAC,IAAI,CACT,WAAW,CAAC,UAAU,EAAE,GAAG,KAAK,kBAAkB,CAAC,CACpD,CAAC;IACJ,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,UAAU,CACjB,KAAc,EACd,QAAgB,EAChB,KAAa,EACb,UAAkB,EAClB,MAAe;IAEf,IAAI,KAAK,KAAK,OAAO,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,OAAO,EAAE,CAAC;QAClE,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QACxB,MAAM,CAAC,IAAI,CACT,WAAW,CACT,UAAU,EACV,GAAG,KAAK,yCAAyC,CAClD,CACF,CAAC;IACJ,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,wBAAwB,CAC/B,KAAc,EACd,QAA8B,EAC9B,KAAa,EACb,UAAkB,EAClB,MAAe;IAEf,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,OAAO,EAAE,CAAC;QAC7C,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QACxB,MAAM,CAAC,IAAI,CACT,WAAW,CACT,UAAU,EACV,GAAG,KAAK,mCAAmC,CAC5C,CACF,CAAC;IACJ,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,WAAW,CAAC,IAAY,EAAE,OAAe;IAChD,OAAO;QACL,IAAI,EAAE,qBAAqB;QAC3B,QAAQ,EAAE,OAAO;QACjB,OAAO;QACP,IAAI;QACJ,IAAI,EAAE,gBAAgB;KACvB,CAAC;AACJ,CAAC;AAED,SAAS,aAAa,CAAC,KAAc;IACnC,IAAI,KAAK,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,MAAM,IAAI,KAAK,EAAE,CAAC;QAC1D,OAAQ,KAA2B,CAAC,IAAI,KAAK,QAAQ,CAAC;IACxD,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,SAAS,WAAW,CAAC,KAAc;IACjC,IAAI,KAAK,YAAY,KAAK,EAAE,CAAC;QAC3B,OAAO,KAAK,CAAC,OAAO,CAAC;IACvB,CAAC;IACD,OAAO,MAAM,CAAC,KAAK,CAAC,CAAC;AACvB,CAAC;AAED,SAAS,QAAQ,CAAC,KAAc;IAC9B,OAAO,KAAK,KAAK,IAAI,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;AAC9E,CAAC"}
@@ -0,0 +1,13 @@
1
+ import type { QfaiConfig } from "./config.js";
2
+ export type ContractIndex = {
3
+ ids: Set<string>;
4
+ idToFiles: Map<string, Set<string>>;
5
+ files: {
6
+ ui: string[];
7
+ api: string[];
8
+ data: string[];
9
+ };
10
+ structuredParseFailedFiles: Set<string>;
11
+ };
12
+ export declare function buildContractIndex(root: string, config: QfaiConfig): Promise<ContractIndex>;
13
+ //# sourceMappingURL=contractIndex.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"contractIndex.d.ts","sourceRoot":"","sources":["../../src/core/contractIndex.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAc9C,MAAM,MAAM,aAAa,GAAG;IAC1B,GAAG,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;IACjB,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC,CAAC;IACpC,KAAK,EAAE;QAAE,EAAE,EAAE,MAAM,EAAE,CAAC;QAAC,GAAG,EAAE,MAAM,EAAE,CAAC;QAAC,IAAI,EAAE,MAAM,EAAE,CAAA;KAAE,CAAC;IACvD,0BAA0B,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;CACzC,CAAC;AAEF,wBAAsB,kBAAkB,CACtC,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,UAAU,GACjB,OAAO,CAAC,aAAa,CAAC,CAwBxB"}
@@ -0,0 +1,66 @@
1
+ import { readFile } from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { resolvePath } from "./config.js";
4
+ import { collectApiContractFiles, collectDataContractFiles, collectUiContractFiles, } from "./discovery.js";
5
+ import { extractApiContractIds, extractUiContractIds, parseStructuredContract, } from "./contracts.js";
6
+ import { extractIds } from "./ids.js";
7
+ export async function buildContractIndex(root, config) {
8
+ const contractsRoot = resolvePath(root, config, "contractsDir");
9
+ const uiRoot = path.join(contractsRoot, "ui");
10
+ const apiRoot = path.join(contractsRoot, "api");
11
+ const dataRoot = path.join(contractsRoot, "db");
12
+ const [uiFiles, apiFiles, dataFiles] = await Promise.all([
13
+ collectUiContractFiles(uiRoot),
14
+ collectApiContractFiles(apiRoot),
15
+ collectDataContractFiles(dataRoot),
16
+ ]);
17
+ const index = {
18
+ ids: new Set(),
19
+ idToFiles: new Map(),
20
+ files: { ui: uiFiles, api: apiFiles, data: dataFiles },
21
+ structuredParseFailedFiles: new Set(),
22
+ };
23
+ await indexUiContracts(uiFiles, index);
24
+ await indexApiContracts(apiFiles, index);
25
+ await indexDataContracts(dataFiles, index);
26
+ return index;
27
+ }
28
+ async function indexUiContracts(files, index) {
29
+ for (const file of files) {
30
+ const text = await readFile(file, "utf-8");
31
+ try {
32
+ const doc = parseStructuredContract(file, text);
33
+ extractUiContractIds(doc).forEach((id) => record(index, id, file));
34
+ }
35
+ catch {
36
+ index.structuredParseFailedFiles.add(file);
37
+ extractIds(text, "UI").forEach((id) => record(index, id, file));
38
+ }
39
+ }
40
+ }
41
+ async function indexApiContracts(files, index) {
42
+ for (const file of files) {
43
+ const text = await readFile(file, "utf-8");
44
+ try {
45
+ const doc = parseStructuredContract(file, text);
46
+ extractApiContractIds(doc).forEach((id) => record(index, id, file));
47
+ }
48
+ catch {
49
+ index.structuredParseFailedFiles.add(file);
50
+ extractIds(text, "API").forEach((id) => record(index, id, file));
51
+ }
52
+ }
53
+ }
54
+ async function indexDataContracts(files, index) {
55
+ for (const file of files) {
56
+ const text = await readFile(file, "utf-8");
57
+ extractIds(text, "DATA").forEach((id) => record(index, id, file));
58
+ }
59
+ }
60
+ function record(index, id, file) {
61
+ index.ids.add(id);
62
+ const current = index.idToFiles.get(id) ?? new Set();
63
+ current.add(file);
64
+ index.idToFiles.set(id, current);
65
+ }
66
+ //# sourceMappingURL=contractIndex.js.map