docspec 0.1.0

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 (42) hide show
  1. package/README.md +121 -0
  2. package/dist/__tests__/cli.test.d.ts +2 -0
  3. package/dist/__tests__/cli.test.d.ts.map +1 -0
  4. package/dist/__tests__/cli.test.js +257 -0
  5. package/dist/__tests__/cli.test.js.map +1 -0
  6. package/dist/__tests__/constants.test.d.ts +2 -0
  7. package/dist/__tests__/constants.test.d.ts.map +1 -0
  8. package/dist/__tests__/constants.test.js +67 -0
  9. package/dist/__tests__/constants.test.js.map +1 -0
  10. package/dist/__tests__/generator.test.d.ts +2 -0
  11. package/dist/__tests__/generator.test.d.ts.map +1 -0
  12. package/dist/__tests__/generator.test.js +118 -0
  13. package/dist/__tests__/generator.test.js.map +1 -0
  14. package/dist/__tests__/validator.test.d.ts +2 -0
  15. package/dist/__tests__/validator.test.d.ts.map +1 -0
  16. package/dist/__tests__/validator.test.js +375 -0
  17. package/dist/__tests__/validator.test.js.map +1 -0
  18. package/dist/cli.d.ts +3 -0
  19. package/dist/cli.d.ts.map +1 -0
  20. package/dist/cli.js +134 -0
  21. package/dist/cli.js.map +1 -0
  22. package/dist/constants.d.ts +13 -0
  23. package/dist/constants.d.ts.map +1 -0
  24. package/dist/constants.js +55 -0
  25. package/dist/constants.js.map +1 -0
  26. package/dist/generator.d.ts +12 -0
  27. package/dist/generator.d.ts.map +1 -0
  28. package/dist/generator.js +77 -0
  29. package/dist/generator.js.map +1 -0
  30. package/dist/index.d.ts +8 -0
  31. package/dist/index.d.ts.map +1 -0
  32. package/dist/index.js +15 -0
  33. package/dist/index.js.map +1 -0
  34. package/dist/types.d.ts +16 -0
  35. package/dist/types.d.ts.map +1 -0
  36. package/dist/types.js +3 -0
  37. package/dist/types.js.map +1 -0
  38. package/dist/validator.d.ts +7 -0
  39. package/dist/validator.d.ts.map +1 -0
  40. package/dist/validator.js +173 -0
  41. package/dist/validator.js.map +1 -0
  42. package/package.json +38 -0
package/README.md ADDED
@@ -0,0 +1,121 @@
1
+ # docspec
2
+
3
+ Generate and validate docspec files (`*.docspec.md`) with a standardized 5-section format.
4
+
5
+ ## Installation
6
+
7
+ ```bash
8
+ npm install docspec
9
+ ```
10
+
11
+ Or install globally:
12
+
13
+ ```bash
14
+ npm install -g docspec
15
+ ```
16
+
17
+ ## Usage
18
+
19
+ ### CLI Commands
20
+
21
+ #### Validate docspec files
22
+
23
+ Validate specific files:
24
+
25
+ ```bash
26
+ docspec validate path/to/file.docspec.md
27
+ ```
28
+
29
+ Or validate all `*.docspec.md` files in the current directory tree:
30
+
31
+ ```bash
32
+ docspec validate
33
+ ```
34
+
35
+ #### Generate a new docspec file
36
+
37
+ ```bash
38
+ docspec generate path/to/new-file.docspec.md
39
+ ```
40
+
41
+ Optionally specify a document name:
42
+
43
+ ```bash
44
+ docspec generate path/to/new-file.docspec.md --name "My Document"
45
+ ```
46
+
47
+ ### Library Usage
48
+
49
+ ```typescript
50
+ import { validateDocspec, generateDocspec } from "docspec";
51
+
52
+ // Validate a file
53
+ const result = await validateDocspec("path/to/file.docspec.md");
54
+ if (!result.valid) {
55
+ console.error("Validation errors:", result.errors);
56
+ }
57
+
58
+ // Generate a new docspec file
59
+ await generateDocspec("path/to/new-file.docspec.md", "Document Name");
60
+ ```
61
+
62
+ ## Pre-commit Integration
63
+
64
+ To use docspec with [pre-commit](https://pre-commit.com/), add the following to your `.pre-commit-config.yaml`:
65
+
66
+ ```yaml
67
+ repos:
68
+ - repo: local
69
+ hooks:
70
+ - id: docspec-validate
71
+ name: Validate docspec files
72
+ entry: docspec validate
73
+ language: system
74
+ files: \.docspec\.md$
75
+ pass_filenames: true
76
+ ```
77
+
78
+ Then install the pre-commit hooks:
79
+
80
+ ```bash
81
+ pre-commit install
82
+ ```
83
+
84
+ The hook will automatically validate any modified `*.docspec.md` files on commit.
85
+
86
+ ## Docspec Format
87
+
88
+ A docspec file must contain the following 5 sections:
89
+
90
+ 1. **Purpose of This Document** - Explain what this Markdown file is supposed to achieve
91
+ 2. **When This Document Should Be Updated** - Describe triggers based on code changes
92
+ 3. **Structure & Required Sections** - Describe expected sections and what belongs in them
93
+ 4. **Style & Editing Guidelines** - Rules specific to this doc or directory
94
+ 5. **Known Gaps or Intentional Omissions** - Things that should not be documented yet
95
+
96
+ Each section must be customized and cannot contain only the boilerplate template text.
97
+
98
+ ## Development
99
+
100
+ ### Running Tests
101
+
102
+ ```bash
103
+ npm test
104
+ ```
105
+
106
+ Run tests in watch mode:
107
+
108
+ ```bash
109
+ npm run test:watch
110
+ ```
111
+
112
+ ### Building
113
+
114
+ ```bash
115
+ npm run build
116
+ ```
117
+
118
+ ## License
119
+
120
+ MIT
121
+
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=cli.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.test.d.ts","sourceRoot":"","sources":["../../src/__tests__/cli.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,257 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ const fs = __importStar(require("fs/promises"));
37
+ const path = __importStar(require("path"));
38
+ const os = __importStar(require("os"));
39
+ const child_process_1 = require("child_process");
40
+ const util_1 = require("util");
41
+ const generator_1 = require("../generator");
42
+ const execAsync = (0, util_1.promisify)(child_process_1.exec);
43
+ describe("CLI", () => {
44
+ let tempDir;
45
+ let originalCwd;
46
+ beforeEach(async () => {
47
+ tempDir = await fs.mkdtemp(path.join(os.tmpdir(), "docspec-cli-test-"));
48
+ originalCwd = process.cwd();
49
+ process.chdir(tempDir);
50
+ });
51
+ afterEach(async () => {
52
+ process.chdir(originalCwd);
53
+ await fs.rm(tempDir, { recursive: true, force: true });
54
+ });
55
+ const runCli = async (args) => {
56
+ const cliPath = path.join(__dirname, "../../dist/cli.js");
57
+ try {
58
+ const { stdout, stderr } = await execAsync(`node ${cliPath} ${args}`);
59
+ return { stdout: stdout || "", stderr: stderr || "", code: 0 };
60
+ }
61
+ catch (error) {
62
+ return {
63
+ stdout: error.stdout || "",
64
+ stderr: error.stderr || "",
65
+ code: error.code || 1,
66
+ };
67
+ }
68
+ };
69
+ describe("validate command", () => {
70
+ it("should validate a valid docspec file", async () => {
71
+ const filePath = path.join(tempDir, "valid.docspec.md");
72
+ const validContent = `---
73
+
74
+ # DOCSPEC: Test
75
+
76
+ ---
77
+
78
+ ## 1. Purpose of This Document
79
+
80
+ This document serves as a test case for the CLI validation command. It contains custom content that is different from the boilerplate template and sufficient to pass validation.
81
+
82
+ ## 2. When This Document Should Be Updated
83
+
84
+ This document should be updated when testing CLI validation functionality. The content is meaningful and customized for testing purposes.
85
+
86
+ ## 3. Structure & Required Sections
87
+
88
+ This section describes the structure of the test document. It includes all required sections with adequate content to pass validation checks.
89
+
90
+ ## 4. Style & Editing Guidelines
91
+
92
+ The style for this test document is straightforward and technical. It focuses on clarity and precision in describing test scenarios. Do: Ensure all sections have adequate content. Don't: Use boilerplate text or leave sections empty. Always provide meaningful test data.
93
+
94
+ ## 5. Known Gaps or Intentional Omissions
95
+
96
+ There are no known gaps in this test document. All sections are complete and properly formatted with sufficient content.
97
+ `;
98
+ await fs.writeFile(filePath, validContent, "utf-8");
99
+ const result = await runCli(`validate ${filePath}`);
100
+ expect(result.code).toBe(0);
101
+ expect(result.stdout).toContain("✅");
102
+ });
103
+ it("should reject an invalid docspec file", async () => {
104
+ const filePath = path.join(tempDir, "invalid.docspec.md");
105
+ await (0, generator_1.generateDocspec)(filePath, "Test"); // This creates boilerplate-only content
106
+ const result = await runCli(`validate ${filePath}`);
107
+ expect(result.code).toBe(1);
108
+ const output = result.stdout + result.stderr;
109
+ expect(output).toContain("❌");
110
+ expect(output).toContain("boilerplate");
111
+ });
112
+ it("should validate multiple files", async () => {
113
+ const file1 = path.join(tempDir, "file1.docspec.md");
114
+ const file2 = path.join(tempDir, "file2.docspec.md");
115
+ const validContent = `---
116
+
117
+ # DOCSPEC: Test
118
+
119
+ ---
120
+
121
+ ## 1. Purpose of This Document
122
+
123
+ This document serves as a test case for validating multiple docspec files. It contains custom content that is different from the boilerplate template.
124
+
125
+ ## 2. When This Document Should Be Updated
126
+
127
+ This document should be updated when testing multiple file validation. The content is meaningful and customized for testing purposes.
128
+
129
+ ## 3. Structure & Required Sections
130
+
131
+ This section describes the structure of the test document. It includes all required sections with adequate content to pass validation checks.
132
+
133
+ ## 4. Style & Editing Guidelines
134
+
135
+ The style for this test document is straightforward and technical. It focuses on clarity and precision in describing test scenarios. Do: Ensure all sections have adequate content. Don't: Use boilerplate text or leave sections empty. Always provide meaningful test data.
136
+
137
+ ## 5. Known Gaps or Intentional Omissions
138
+
139
+ There are no known gaps in this test document. All sections are complete and properly formatted with sufficient content.
140
+ `;
141
+ await fs.writeFile(file1, validContent, "utf-8");
142
+ await fs.writeFile(file2, validContent, "utf-8");
143
+ const result = await runCli(`validate ${file1} ${file2}`);
144
+ expect(result.code).toBe(0);
145
+ expect(result.stdout).toContain("file1.docspec.md");
146
+ expect(result.stdout).toContain("file2.docspec.md");
147
+ });
148
+ it("should find all docspec files when no paths provided", async () => {
149
+ const file1 = path.join(tempDir, "file1.docspec.md");
150
+ const file2 = path.join(tempDir, "nested", "file2.docspec.md");
151
+ await fs.mkdir(path.join(tempDir, "nested"), { recursive: true });
152
+ const validContent = `---
153
+
154
+ # DOCSPEC: Test
155
+
156
+ ---
157
+
158
+ ## 1. Purpose of This Document
159
+
160
+ This document serves as a test case for validating multiple docspec files. It contains custom content that is different from the boilerplate template.
161
+
162
+ ## 2. When This Document Should Be Updated
163
+
164
+ This document should be updated when testing multiple file validation. The content is meaningful and customized for testing purposes.
165
+
166
+ ## 3. Structure & Required Sections
167
+
168
+ This section describes the structure of the test document. It includes all required sections with adequate content to pass validation checks.
169
+
170
+ ## 4. Style & Editing Guidelines
171
+
172
+ The style for this test document is straightforward and technical. It focuses on clarity and precision in describing test scenarios. Do: Ensure all sections have adequate content. Don't: Use boilerplate text or leave sections empty. Always provide meaningful test data.
173
+
174
+ ## 5. Known Gaps or Intentional Omissions
175
+
176
+ There are no known gaps in this test document. All sections are complete and properly formatted with sufficient content.
177
+ `;
178
+ await fs.writeFile(file1, validContent, "utf-8");
179
+ await fs.writeFile(file2, validContent, "utf-8");
180
+ const result = await runCli("validate");
181
+ expect(result.code).toBe(0);
182
+ expect(result.stdout).toContain("file1.docspec.md");
183
+ expect(result.stdout).toContain("file2.docspec.md");
184
+ });
185
+ it("should handle non-existent files gracefully", async () => {
186
+ const result = await runCli("validate nonexistent.docspec.md");
187
+ expect(result.code).toBe(1);
188
+ const output = result.stdout + result.stderr;
189
+ expect(output).toContain("Failed to read file");
190
+ });
191
+ it("should skip node_modules and .git directories", async () => {
192
+ await fs.mkdir(path.join(tempDir, "node_modules"), { recursive: true });
193
+ await fs.mkdir(path.join(tempDir, ".git"), { recursive: true });
194
+ const fileInNodeModules = path.join(tempDir, "node_modules", "test.docspec.md");
195
+ const fileInGit = path.join(tempDir, ".git", "test.docspec.md");
196
+ await fs.writeFile(fileInNodeModules, "test", "utf-8");
197
+ await fs.writeFile(fileInGit, "test", "utf-8");
198
+ const result = await runCli("validate");
199
+ // Should not find files in node_modules or .git
200
+ expect(result.stdout).not.toContain("node_modules");
201
+ expect(result.stdout).not.toContain(".git");
202
+ });
203
+ });
204
+ describe("generate command", () => {
205
+ it("should generate a new docspec file", async () => {
206
+ const filePath = path.join(tempDir, "new.docspec.md");
207
+ const result = await runCli(`generate ${filePath} --name "Test Document"`);
208
+ expect(result.code).toBe(0);
209
+ expect(result.stdout).toContain("✅");
210
+ expect(result.stdout).toContain("new.docspec.md");
211
+ const exists = await fs.access(filePath).then(() => true).catch(() => false);
212
+ expect(exists).toBe(true);
213
+ });
214
+ it("should generate file with correct content", async () => {
215
+ const filePath = path.join(tempDir, "test.docspec.md");
216
+ await runCli(`generate ${filePath} --name "My Document"`);
217
+ const content = await fs.readFile(filePath, "utf-8");
218
+ expect(content).toContain("# DOCSPEC: My Document");
219
+ expect(content).toContain("Purpose of This Document");
220
+ });
221
+ it("should auto-append .docspec.md if not present", async () => {
222
+ const filePath = path.join(tempDir, "test");
223
+ await runCli(`generate ${filePath} --name "Test"`);
224
+ const fullPath = filePath + ".docspec.md";
225
+ const exists = await fs.access(fullPath).then(() => true).catch(() => false);
226
+ expect(exists).toBe(true);
227
+ });
228
+ it("should create nested directories", async () => {
229
+ const filePath = path.join(tempDir, "nested", "deep", "test.docspec.md");
230
+ const result = await runCli(`generate ${filePath} --name "Test"`);
231
+ expect(result.code).toBe(0);
232
+ const exists = await fs.access(filePath).then(() => true).catch(() => false);
233
+ expect(exists).toBe(true);
234
+ });
235
+ it("should extract name from filename if not provided", async () => {
236
+ const filePath = path.join(tempDir, "my-awesome-doc.docspec.md");
237
+ await runCli(`generate ${filePath}`);
238
+ const content = await fs.readFile(filePath, "utf-8");
239
+ expect(content).toContain("# DOCSPEC: My Awesome Doc");
240
+ });
241
+ });
242
+ describe("help and version", () => {
243
+ it("should show help message", async () => {
244
+ const result = await runCli("--help");
245
+ expect(result.code).toBe(0);
246
+ expect(result.stdout).toContain("Usage:");
247
+ expect(result.stdout).toContain("validate");
248
+ expect(result.stdout).toContain("generate");
249
+ });
250
+ it("should show version", async () => {
251
+ const result = await runCli("--version");
252
+ expect(result.code).toBe(0);
253
+ expect(result.stdout).toContain("0.1.0");
254
+ });
255
+ });
256
+ });
257
+ //# sourceMappingURL=cli.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.test.js","sourceRoot":"","sources":["../../src/__tests__/cli.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=constants.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.test.d.ts","sourceRoot":"","sources":["../../src/__tests__/constants.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,67 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const constants_1 = require("../constants");
4
+ describe("constants", () => {
5
+ describe("REQUIRED_SECTIONS", () => {
6
+ it("should have exactly 5 required sections", () => {
7
+ expect(constants_1.REQUIRED_SECTIONS).toHaveLength(5);
8
+ });
9
+ it("should contain all expected section names", () => {
10
+ const expectedSections = [
11
+ "Purpose of This Document",
12
+ "When This Document Should Be Updated",
13
+ "Structure & Required Sections",
14
+ "Style & Editing Guidelines",
15
+ "Known Gaps or Intentional Omissions",
16
+ ];
17
+ expectedSections.forEach((section) => {
18
+ expect(constants_1.REQUIRED_SECTIONS).toContain(section);
19
+ });
20
+ });
21
+ });
22
+ describe("SECTION_BOILERPLATE", () => {
23
+ it("should have boilerplate for all required sections", () => {
24
+ constants_1.REQUIRED_SECTIONS.forEach((section) => {
25
+ expect(constants_1.SECTION_BOILERPLATE[section]).toBeDefined();
26
+ expect(constants_1.SECTION_BOILERPLATE[section].length).toBeGreaterThan(0);
27
+ });
28
+ });
29
+ });
30
+ describe("getDocspecTemplate", () => {
31
+ it("should generate a template with the document name", () => {
32
+ const template = (0, constants_1.getDocspecTemplate)("Test Document");
33
+ expect(template).toContain("# DOCSPEC: Test Document");
34
+ });
35
+ it("should include all 5 required sections", () => {
36
+ const template = (0, constants_1.getDocspecTemplate)("Test");
37
+ constants_1.REQUIRED_SECTIONS.forEach((section) => {
38
+ expect(template).toContain(section);
39
+ });
40
+ });
41
+ it("should include section numbers", () => {
42
+ const template = (0, constants_1.getDocspecTemplate)("Test");
43
+ for (let i = 1; i <= 5; i++) {
44
+ expect(template).toContain(`## ${i}.`);
45
+ }
46
+ });
47
+ it("should include boilerplate content for each section", () => {
48
+ const template = (0, constants_1.getDocspecTemplate)("Test");
49
+ constants_1.REQUIRED_SECTIONS.forEach((section) => {
50
+ const boilerplate = constants_1.SECTION_BOILERPLATE[section];
51
+ // Check that at least part of the boilerplate is present
52
+ expect(template).toContain(boilerplate.split("\n")[0]);
53
+ });
54
+ });
55
+ it("should include separators between sections", () => {
56
+ const template = (0, constants_1.getDocspecTemplate)("Test");
57
+ // Should have separators for 5 sections
58
+ const separatorCount = (template.match(/^---$/gm) || []).length;
59
+ expect(separatorCount).toBeGreaterThanOrEqual(2); // At least front matter and between sections
60
+ });
61
+ it("should have proper front matter format", () => {
62
+ const template = (0, constants_1.getDocspecTemplate)("Test");
63
+ expect(template).toMatch(/^---\n/);
64
+ });
65
+ });
66
+ });
67
+ //# sourceMappingURL=constants.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.test.js","sourceRoot":"","sources":["../../src/__tests__/constants.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=generator.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"generator.test.d.ts","sourceRoot":"","sources":["../../src/__tests__/generator.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,118 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ const fs = __importStar(require("fs/promises"));
37
+ const path = __importStar(require("path"));
38
+ const os = __importStar(require("os"));
39
+ const generator_1 = require("../generator");
40
+ const constants_1 = require("../constants");
41
+ describe("generator", () => {
42
+ let tempDir;
43
+ beforeEach(async () => {
44
+ tempDir = await fs.mkdtemp(path.join(os.tmpdir(), "docspec-test-"));
45
+ });
46
+ afterEach(async () => {
47
+ await fs.rm(tempDir, { recursive: true, force: true });
48
+ });
49
+ describe("generateDocspecContent", () => {
50
+ it("should generate content with the provided name", () => {
51
+ const content = (0, generator_1.generateDocspecContent)("My Test Document");
52
+ expect(content).toContain("# DOCSPEC: My Test Document");
53
+ });
54
+ it("should include all required sections", () => {
55
+ const content = (0, generator_1.generateDocspecContent)("Test");
56
+ constants_1.REQUIRED_SECTIONS.forEach((section) => {
57
+ expect(content).toContain(section);
58
+ });
59
+ });
60
+ });
61
+ describe("generateDocspec", () => {
62
+ it("should generate a file at the specified path", async () => {
63
+ const filePath = path.join(tempDir, "test.docspec.md");
64
+ await (0, generator_1.generateDocspec)(filePath, "Test Document");
65
+ const exists = await fs.access(filePath).then(() => true).catch(() => false);
66
+ expect(exists).toBe(true);
67
+ });
68
+ it("should use provided document name", async () => {
69
+ const filePath = path.join(tempDir, "test.docspec.md");
70
+ await (0, generator_1.generateDocspec)(filePath, "Custom Name");
71
+ const content = await fs.readFile(filePath, "utf-8");
72
+ expect(content).toContain("# DOCSPEC: Custom Name");
73
+ });
74
+ it("should extract name from file path if not provided", async () => {
75
+ const filePath = path.join(tempDir, "my-awesome-doc.docspec.md");
76
+ await (0, generator_1.generateDocspec)(filePath);
77
+ const content = await fs.readFile(filePath, "utf-8");
78
+ expect(content).toContain("# DOCSPEC: My Awesome Doc");
79
+ });
80
+ it("should handle kebab-case filenames", async () => {
81
+ const filePath = path.join(tempDir, "api-reference.docspec.md");
82
+ await (0, generator_1.generateDocspec)(filePath);
83
+ const content = await fs.readFile(filePath, "utf-8");
84
+ expect(content).toContain("# DOCSPEC: Api Reference");
85
+ });
86
+ it("should handle snake_case filenames", async () => {
87
+ const filePath = path.join(tempDir, "user_guide.docspec.md");
88
+ await (0, generator_1.generateDocspec)(filePath);
89
+ const content = await fs.readFile(filePath, "utf-8");
90
+ expect(content).toContain("# DOCSPEC: User Guide");
91
+ });
92
+ it("should create parent directories if they don't exist", async () => {
93
+ const filePath = path.join(tempDir, "nested", "deep", "test.docspec.md");
94
+ await (0, generator_1.generateDocspec)(filePath, "Test");
95
+ const exists = await fs.access(filePath).then(() => true).catch(() => false);
96
+ expect(exists).toBe(true);
97
+ });
98
+ it("should generate valid markdown content", async () => {
99
+ const filePath = path.join(tempDir, "test.docspec.md");
100
+ await (0, generator_1.generateDocspec)(filePath, "Test");
101
+ const content = await fs.readFile(filePath, "utf-8");
102
+ // Check structure
103
+ expect(content).toContain("---");
104
+ expect(content).toContain("# DOCSPEC:");
105
+ expect(content).toContain("## 1.");
106
+ expect(content).toContain("## 5.");
107
+ });
108
+ it("should include all required sections in generated file", async () => {
109
+ const filePath = path.join(tempDir, "test.docspec.md");
110
+ await (0, generator_1.generateDocspec)(filePath, "Test");
111
+ const content = await fs.readFile(filePath, "utf-8");
112
+ constants_1.REQUIRED_SECTIONS.forEach((section) => {
113
+ expect(content).toContain(section);
114
+ });
115
+ });
116
+ });
117
+ });
118
+ //# sourceMappingURL=generator.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"generator.test.js","sourceRoot":"","sources":["../../src/__tests__/generator.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=validator.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validator.test.d.ts","sourceRoot":"","sources":["../../src/__tests__/validator.test.ts"],"names":[],"mappings":""}