@aigne/doc-smith 0.8.12-beta.8 → 0.8.12-beta.9

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 (264) hide show
  1. package/CHANGELOG.md +13 -0
  2. package/agents/publish/index.yaml +4 -0
  3. package/agents/publish/publish-docs.mjs +77 -5
  4. package/agents/publish/translate-meta.mjs +103 -0
  5. package/agents/update/generate-document.yaml +30 -28
  6. package/agents/update/update-document-detail.yaml +3 -1
  7. package/agents/utils/update-branding.mjs +69 -0
  8. package/package.json +16 -2
  9. package/prompts/common/document/role-and-personality.md +3 -1
  10. package/prompts/detail/d2-diagram/guide.md +7 -1
  11. package/prompts/detail/d2-diagram/user-prompt.md +3 -0
  12. package/prompts/detail/generate/system-prompt.md +6 -7
  13. package/prompts/detail/generate/user-prompt.md +12 -3
  14. package/prompts/detail/update/user-prompt.md +0 -2
  15. package/prompts/structure/update/user-prompt.md +0 -4
  16. package/utils/file-utils.mjs +69 -24
  17. package/utils/markdown-checker.mjs +0 -20
  18. package/utils/request.mjs +7 -0
  19. package/utils/upload-files.mjs +231 -0
  20. package/utils/utils.mjs +11 -1
  21. package/.aigne/doc-smith/config.yaml +0 -77
  22. package/.aigne/doc-smith/history.yaml +0 -37
  23. package/.aigne/doc-smith/media-description.yaml +0 -91
  24. package/.aigne/doc-smith/output/structure-plan.json +0 -162
  25. package/.aigne/doc-smith/preferences.yml +0 -97
  26. package/.aigne/doc-smith/upload-cache.yaml +0 -1830
  27. package/.github/PULL_REQUEST_TEMPLATE.md +0 -28
  28. package/.github/workflows/ci.yml +0 -54
  29. package/.github/workflows/create-release-pr.yaml +0 -21
  30. package/.github/workflows/publish-docs.yml +0 -65
  31. package/.github/workflows/release.yml +0 -49
  32. package/.github/workflows/reviewer.yml +0 -54
  33. package/.release-please-manifest.json +0 -3
  34. package/RELEASE.md +0 -9
  35. package/assets/screenshots/doc-complete-setup.png +0 -0
  36. package/assets/screenshots/doc-generate-docs.png +0 -0
  37. package/assets/screenshots/doc-generate.png +0 -0
  38. package/assets/screenshots/doc-generated-successfully.png +0 -0
  39. package/assets/screenshots/doc-publish.png +0 -0
  40. package/assets/screenshots/doc-regenerate.png +0 -0
  41. package/assets/screenshots/doc-translate-langs.png +0 -0
  42. package/assets/screenshots/doc-translate.png +0 -0
  43. package/assets/screenshots/doc-update.png +0 -0
  44. package/biome.json +0 -73
  45. package/codecov.yml +0 -15
  46. package/docs/_sidebar.md +0 -15
  47. package/docs/configuration-initial-setup.ja.md +0 -179
  48. package/docs/configuration-initial-setup.md +0 -198
  49. package/docs/configuration-initial-setup.zh-TW.md +0 -179
  50. package/docs/configuration-initial-setup.zh.md +0 -179
  51. package/docs/configuration-managing-preferences.ja.md +0 -100
  52. package/docs/configuration-managing-preferences.md +0 -100
  53. package/docs/configuration-managing-preferences.zh-TW.md +0 -100
  54. package/docs/configuration-managing-preferences.zh.md +0 -100
  55. package/docs/configuration.ja.md +0 -69
  56. package/docs/configuration.md +0 -69
  57. package/docs/configuration.zh-TW.md +0 -69
  58. package/docs/configuration.zh.md +0 -69
  59. package/docs/getting-started.ja.md +0 -107
  60. package/docs/getting-started.md +0 -107
  61. package/docs/getting-started.zh-TW.md +0 -107
  62. package/docs/getting-started.zh.md +0 -107
  63. package/docs/guides-cleaning-up.ja.md +0 -51
  64. package/docs/guides-cleaning-up.md +0 -52
  65. package/docs/guides-cleaning-up.zh-TW.md +0 -51
  66. package/docs/guides-cleaning-up.zh.md +0 -51
  67. package/docs/guides-evaluating-documents.ja.md +0 -66
  68. package/docs/guides-evaluating-documents.md +0 -107
  69. package/docs/guides-evaluating-documents.zh-TW.md +0 -66
  70. package/docs/guides-evaluating-documents.zh.md +0 -66
  71. package/docs/guides-generating-documentation.ja.md +0 -151
  72. package/docs/guides-generating-documentation.md +0 -89
  73. package/docs/guides-generating-documentation.zh-TW.md +0 -151
  74. package/docs/guides-generating-documentation.zh.md +0 -151
  75. package/docs/guides-interactive-chat.ja.md +0 -85
  76. package/docs/guides-interactive-chat.md +0 -93
  77. package/docs/guides-interactive-chat.zh-TW.md +0 -85
  78. package/docs/guides-interactive-chat.zh.md +0 -85
  79. package/docs/guides-managing-history.ja.md +0 -48
  80. package/docs/guides-managing-history.md +0 -53
  81. package/docs/guides-managing-history.zh-TW.md +0 -48
  82. package/docs/guides-managing-history.zh.md +0 -48
  83. package/docs/guides-publishing-your-docs.ja.md +0 -78
  84. package/docs/guides-publishing-your-docs.md +0 -83
  85. package/docs/guides-publishing-your-docs.zh-TW.md +0 -78
  86. package/docs/guides-publishing-your-docs.zh.md +0 -78
  87. package/docs/guides-translating-documentation.ja.md +0 -95
  88. package/docs/guides-translating-documentation.md +0 -100
  89. package/docs/guides-translating-documentation.zh-TW.md +0 -95
  90. package/docs/guides-translating-documentation.zh.md +0 -95
  91. package/docs/guides-updating-documentation.ja.md +0 -77
  92. package/docs/guides-updating-documentation.md +0 -79
  93. package/docs/guides-updating-documentation.zh-TW.md +0 -77
  94. package/docs/guides-updating-documentation.zh.md +0 -77
  95. package/docs/guides.ja.md +0 -32
  96. package/docs/guides.md +0 -32
  97. package/docs/guides.zh-TW.md +0 -32
  98. package/docs/guides.zh.md +0 -32
  99. package/docs/overview.ja.md +0 -61
  100. package/docs/overview.md +0 -61
  101. package/docs/overview.zh-TW.md +0 -61
  102. package/docs/overview.zh.md +0 -61
  103. package/docs/release-notes.ja.md +0 -255
  104. package/docs/release-notes.md +0 -288
  105. package/docs/release-notes.zh-TW.md +0 -255
  106. package/docs/release-notes.zh.md +0 -255
  107. package/prompts/common/afs/afs-tools-usage.md +0 -5
  108. package/prompts/common/afs/use-afs-instruction.md +0 -1
  109. package/release-please-config.json +0 -14
  110. package/tests/agents/chat/chat.test.mjs +0 -46
  111. package/tests/agents/clear/choose-contents.test.mjs +0 -284
  112. package/tests/agents/clear/clear-auth-tokens.test.mjs +0 -268
  113. package/tests/agents/clear/clear-document-config.test.mjs +0 -167
  114. package/tests/agents/clear/clear-document-structure.test.mjs +0 -380
  115. package/tests/agents/clear/clear-generated-docs.test.mjs +0 -222
  116. package/tests/agents/evaluate/code-snippet.test.mjs +0 -163
  117. package/tests/agents/evaluate/fixtures/api-services.md +0 -87
  118. package/tests/agents/evaluate/fixtures/js-sdk.md +0 -94
  119. package/tests/agents/evaluate/generate-report.test.mjs +0 -312
  120. package/tests/agents/generate/check-document-structure.test.mjs +0 -45
  121. package/tests/agents/generate/check-need-generate-structure.test.mjs +0 -279
  122. package/tests/agents/generate/document-structure-tools/add-document.test.mjs +0 -449
  123. package/tests/agents/generate/document-structure-tools/delete-document.test.mjs +0 -410
  124. package/tests/agents/generate/document-structure-tools/generate-sub-structure.test.mjs +0 -277
  125. package/tests/agents/generate/document-structure-tools/move-document.test.mjs +0 -476
  126. package/tests/agents/generate/document-structure-tools/update-document.test.mjs +0 -548
  127. package/tests/agents/generate/generate-structure.test.mjs +0 -45
  128. package/tests/agents/generate/user-review-document-structure.test.mjs +0 -319
  129. package/tests/agents/history/view.test.mjs +0 -97
  130. package/tests/agents/init/init.test.mjs +0 -1657
  131. package/tests/agents/prefs/prefs.test.mjs +0 -431
  132. package/tests/agents/publish/publish-docs.test.mjs +0 -787
  133. package/tests/agents/translate/choose-language.test.mjs +0 -311
  134. package/tests/agents/translate/translate-document.test.mjs +0 -51
  135. package/tests/agents/update/check-document.test.mjs +0 -463
  136. package/tests/agents/update/check-update-is-single.test.mjs +0 -300
  137. package/tests/agents/update/document-tools/update-document-content.test.mjs +0 -329
  138. package/tests/agents/update/generate-document.test.mjs +0 -51
  139. package/tests/agents/update/save-and-translate-document.test.mjs +0 -369
  140. package/tests/agents/update/user-review-document.test.mjs +0 -582
  141. package/tests/agents/utils/action-success.test.mjs +0 -54
  142. package/tests/agents/utils/check-detail-result.test.mjs +0 -743
  143. package/tests/agents/utils/check-feedback-refiner.test.mjs +0 -478
  144. package/tests/agents/utils/choose-docs.test.mjs +0 -406
  145. package/tests/agents/utils/exit.test.mjs +0 -70
  146. package/tests/agents/utils/feedback-refiner.test.mjs +0 -51
  147. package/tests/agents/utils/find-item-by-path.test.mjs +0 -517
  148. package/tests/agents/utils/find-user-preferences-by-path.test.mjs +0 -382
  149. package/tests/agents/utils/format-document-structure.test.mjs +0 -364
  150. package/tests/agents/utils/fs.test.mjs +0 -267
  151. package/tests/agents/utils/load-sources.test.mjs +0 -1470
  152. package/tests/agents/utils/save-docs.test.mjs +0 -109
  153. package/tests/agents/utils/save-output.test.mjs +0 -315
  154. package/tests/agents/utils/save-single-doc.test.mjs +0 -364
  155. package/tests/agents/utils/transform-detail-datasources.test.mjs +0 -320
  156. package/tests/utils/auth-utils.test.mjs +0 -596
  157. package/tests/utils/blocklet.test.mjs +0 -336
  158. package/tests/utils/conflict-detector.test.mjs +0 -355
  159. package/tests/utils/constants.test.mjs +0 -295
  160. package/tests/utils/d2-utils.test.mjs +0 -437
  161. package/tests/utils/deploy.test.mjs +0 -399
  162. package/tests/utils/docs-finder-utils.test.mjs +0 -650
  163. package/tests/utils/file-utils.test.mjs +0 -521
  164. package/tests/utils/history-utils.test.mjs +0 -206
  165. package/tests/utils/kroki-utils.test.mjs +0 -646
  166. package/tests/utils/linter/fixtures/css/keyword-error.css +0 -1
  167. package/tests/utils/linter/fixtures/css/missing-semicolon.css +0 -1
  168. package/tests/utils/linter/fixtures/css/syntax-error.css +0 -1
  169. package/tests/utils/linter/fixtures/css/undeclare-variable.css +0 -1
  170. package/tests/utils/linter/fixtures/css/unused-variable.css +0 -2
  171. package/tests/utils/linter/fixtures/css/valid-code.css +0 -1
  172. package/tests/utils/linter/fixtures/dockerfile/keyword-error.dockerfile +0 -1
  173. package/tests/utils/linter/fixtures/dockerfile/missing-semicolon.dockerfile +0 -2
  174. package/tests/utils/linter/fixtures/dockerfile/syntax-error.dockerfile +0 -2
  175. package/tests/utils/linter/fixtures/dockerfile/undeclare-variable.dockerfile +0 -1
  176. package/tests/utils/linter/fixtures/dockerfile/unused-variable.dockerfile +0 -1
  177. package/tests/utils/linter/fixtures/dockerfile/valid-code.dockerfile +0 -2
  178. package/tests/utils/linter/fixtures/go/keyword-error.go +0 -5
  179. package/tests/utils/linter/fixtures/go/missing-semicolon.go +0 -5
  180. package/tests/utils/linter/fixtures/go/syntax-error.go +0 -6
  181. package/tests/utils/linter/fixtures/go/undeclare-variable.go +0 -5
  182. package/tests/utils/linter/fixtures/go/unused-variable.go +0 -5
  183. package/tests/utils/linter/fixtures/go/valid-code.go +0 -7
  184. package/tests/utils/linter/fixtures/js/keyword-error.js +0 -3
  185. package/tests/utils/linter/fixtures/js/missing-semicolon.js +0 -6
  186. package/tests/utils/linter/fixtures/js/syntax-error.js +0 -4
  187. package/tests/utils/linter/fixtures/js/undeclare-variable.js +0 -3
  188. package/tests/utils/linter/fixtures/js/unused-variable.js +0 -7
  189. package/tests/utils/linter/fixtures/js/valid-code.js +0 -15
  190. package/tests/utils/linter/fixtures/json/keyword-error.json +0 -1
  191. package/tests/utils/linter/fixtures/json/missing-semicolon.json +0 -1
  192. package/tests/utils/linter/fixtures/json/syntax-error.json +0 -1
  193. package/tests/utils/linter/fixtures/json/undeclare-variable.json +0 -1
  194. package/tests/utils/linter/fixtures/json/unused-variable.json +0 -1
  195. package/tests/utils/linter/fixtures/json/valid-code.json +0 -1
  196. package/tests/utils/linter/fixtures/jsx/keyword-error.jsx +0 -5
  197. package/tests/utils/linter/fixtures/jsx/missing-semicolon.jsx +0 -5
  198. package/tests/utils/linter/fixtures/jsx/syntax-error.jsx +0 -5
  199. package/tests/utils/linter/fixtures/jsx/undeclare-variable.jsx +0 -5
  200. package/tests/utils/linter/fixtures/jsx/unused-variable.jsx +0 -4
  201. package/tests/utils/linter/fixtures/jsx/valid-code.jsx +0 -5
  202. package/tests/utils/linter/fixtures/python/keyword-error.py +0 -3
  203. package/tests/utils/linter/fixtures/python/missing-semicolon.py +0 -2
  204. package/tests/utils/linter/fixtures/python/syntax-error.py +0 -3
  205. package/tests/utils/linter/fixtures/python/undeclare-variable.py +0 -3
  206. package/tests/utils/linter/fixtures/python/unused-variable.py +0 -6
  207. package/tests/utils/linter/fixtures/python/valid-code.py +0 -12
  208. package/tests/utils/linter/fixtures/ruby/keyword-error.rb +0 -2
  209. package/tests/utils/linter/fixtures/ruby/missing-semicolon.rb +0 -1
  210. package/tests/utils/linter/fixtures/ruby/syntax-error.rb +0 -2
  211. package/tests/utils/linter/fixtures/ruby/undeclare-variable.rb +0 -1
  212. package/tests/utils/linter/fixtures/ruby/unused-variable.rb +0 -2
  213. package/tests/utils/linter/fixtures/ruby/valid-code.rb +0 -1
  214. package/tests/utils/linter/fixtures/sass/keyword-error.sass +0 -2
  215. package/tests/utils/linter/fixtures/sass/missing-semicolon.sass +0 -3
  216. package/tests/utils/linter/fixtures/sass/syntax-error.sass +0 -3
  217. package/tests/utils/linter/fixtures/sass/undeclare-variable.sass +0 -2
  218. package/tests/utils/linter/fixtures/sass/unused-variable.sass +0 -4
  219. package/tests/utils/linter/fixtures/sass/valid-code.sass +0 -2
  220. package/tests/utils/linter/fixtures/scss/keyword-error.scss +0 -1
  221. package/tests/utils/linter/fixtures/scss/missing-semicolon.scss +0 -1
  222. package/tests/utils/linter/fixtures/scss/syntax-error.scss +0 -1
  223. package/tests/utils/linter/fixtures/scss/undeclare-variable.scss +0 -1
  224. package/tests/utils/linter/fixtures/scss/unused-variable.scss +0 -2
  225. package/tests/utils/linter/fixtures/scss/valid-code.scss +0 -1
  226. package/tests/utils/linter/fixtures/shell/keyword-error.sh +0 -5
  227. package/tests/utils/linter/fixtures/shell/missing-semicolon.sh +0 -3
  228. package/tests/utils/linter/fixtures/shell/syntax-error.sh +0 -4
  229. package/tests/utils/linter/fixtures/shell/undeclare-variable.sh +0 -3
  230. package/tests/utils/linter/fixtures/shell/unused-variable.sh +0 -4
  231. package/tests/utils/linter/fixtures/shell/valid-code.sh +0 -3
  232. package/tests/utils/linter/fixtures/ts/keyword-error.ts +0 -1
  233. package/tests/utils/linter/fixtures/ts/missing-semicolon.ts +0 -1
  234. package/tests/utils/linter/fixtures/ts/syntax-error.ts +0 -1
  235. package/tests/utils/linter/fixtures/ts/undeclare-variable.ts +0 -1
  236. package/tests/utils/linter/fixtures/ts/unused-variable.ts +0 -3
  237. package/tests/utils/linter/fixtures/ts/valid-code.ts +0 -3
  238. package/tests/utils/linter/fixtures/tsx/keyword-error.tsx +0 -5
  239. package/tests/utils/linter/fixtures/tsx/missing-semicolon.tsx +0 -5
  240. package/tests/utils/linter/fixtures/tsx/syntax-error.tsx +0 -5
  241. package/tests/utils/linter/fixtures/tsx/undeclare-variable.tsx +0 -6
  242. package/tests/utils/linter/fixtures/tsx/unused-variable.tsx +0 -6
  243. package/tests/utils/linter/fixtures/tsx/valid-code.tsx +0 -5
  244. package/tests/utils/linter/fixtures/vue/keyword-error.vue +0 -6
  245. package/tests/utils/linter/fixtures/vue/missing-semicolon.vue +0 -6
  246. package/tests/utils/linter/fixtures/vue/syntax-error.vue +0 -6
  247. package/tests/utils/linter/fixtures/vue/undeclare-variable.vue +0 -6
  248. package/tests/utils/linter/fixtures/vue/unused-variable.vue +0 -7
  249. package/tests/utils/linter/fixtures/vue/valid-code.vue +0 -6
  250. package/tests/utils/linter/fixtures/yaml/keyword-error.yml +0 -1
  251. package/tests/utils/linter/fixtures/yaml/missing-semicolon.yml +0 -2
  252. package/tests/utils/linter/fixtures/yaml/syntax-error.yml +0 -1
  253. package/tests/utils/linter/fixtures/yaml/undeclare-variable.yml +0 -1
  254. package/tests/utils/linter/fixtures/yaml/unused-variable.yml +0 -2
  255. package/tests/utils/linter/fixtures/yaml/valid-code.yml +0 -3
  256. package/tests/utils/linter/index.test.mjs +0 -440
  257. package/tests/utils/linter/scan-results.mjs +0 -42
  258. package/tests/utils/load-config.test.mjs +0 -141
  259. package/tests/utils/markdown/index.test.mjs +0 -478
  260. package/tests/utils/mermaid-validator.test.mjs +0 -541
  261. package/tests/utils/mock-chat-model.mjs +0 -12
  262. package/tests/utils/preferences-utils.test.mjs +0 -465
  263. package/tests/utils/save-value-to-config.test.mjs +0 -483
  264. package/tests/utils/utils.test.mjs +0 -941
@@ -1,163 +0,0 @@
1
- import { describe, expect, test } from "bun:test";
2
- import fs from "node:fs/promises";
3
- import path, { dirname } from "node:path";
4
- import { fileURLToPath } from "node:url";
5
-
6
- import evaluateDocumentCode from "../../../agents/evaluate/code-snippet.mjs";
7
-
8
- const __filename = fileURLToPath(import.meta.url);
9
- const __dirname = dirname(__filename);
10
-
11
- describe("evaluateDocumentCode", () => {
12
- test(
13
- "should evaluate markdown document",
14
- async () => {
15
- const content = await fs.readFile(path.join(__dirname, "fixtures/js-sdk.md"), "utf-8");
16
- const result = await evaluateDocumentCode({ content });
17
-
18
- expect("codeEvaluation" in result).toEqual(true);
19
- expect(result.codeEvaluation.baseline).toEqual(100);
20
- expect("details" in result.codeEvaluation).toEqual(true);
21
- expect(result.codeEvaluation.details.length).toEqual(0);
22
- expect(result.codeEvaluation.totalCount).toEqual(3);
23
- expect(result.codeEvaluation.errorCount).toEqual(0);
24
- expect(result.codeEvaluation.ignoreCount).toEqual(0);
25
- },
26
- 60 * 1000,
27
- );
28
-
29
- test(
30
- "should evaluate markdown document with error",
31
- async () => {
32
- const content = await fs.readFile(path.join(__dirname, "fixtures/api-services.md"), "utf-8");
33
- const result = await evaluateDocumentCode({ content });
34
-
35
- expect(result.codeEvaluation.details.length).toEqual(2);
36
- expect(result.codeEvaluation.totalCount).toEqual(1);
37
- expect(result.codeEvaluation.errorCount).toEqual(1);
38
- expect(result.codeEvaluation.ignoreCount).toEqual(1);
39
- },
40
- 60 * 1000,
41
- );
42
-
43
- test(
44
- "should handle linter failures with retry mechanism",
45
- async () => {
46
- // Since we can't easily mock ES modules, we'll mock the global fetch used by lintCode
47
- const originalFetch = globalThis.fetch;
48
- let callCount = 0;
49
-
50
- // Mock fetch to simulate linter API failures
51
- globalThis.fetch = async (_url, _options) => {
52
- callCount++;
53
- if (callCount <= 2) {
54
- // Fail the first 2 attempts
55
- throw new Error(`Network error ${callCount}`);
56
- }
57
- // Succeed on the third attempt with a valid response
58
- return {
59
- ok: true,
60
- json: async () => ({
61
- success: true,
62
- issues: [],
63
- }),
64
- };
65
- };
66
-
67
- try {
68
- // Create markdown content with code blocks that will trigger linting
69
- const content = `
70
- # Test Document
71
-
72
- \`\`\`javascript
73
- console.log("test");
74
- \`\`\`
75
- `;
76
-
77
- const result = await evaluateDocumentCode({ content });
78
-
79
- // Verify the function completed successfully despite initial failures
80
- expect(result.codeEvaluation).toBeDefined();
81
- expect(result.codeEvaluation.totalCount).toBe(1);
82
-
83
- // With fetch mocking, if retries work, we should get a successful result
84
- // The exact behavior depends on how the retries are handled
85
- } finally {
86
- // Restore the original fetch function
87
- globalThis.fetch = originalFetch;
88
- }
89
- },
90
- 120 * 1000, // Longer timeout for retry testing
91
- );
92
-
93
- test(
94
- "should handle persistent linter failures after retries",
95
- async () => {
96
- // Mock fetch to always fail
97
- const originalFetch = globalThis.fetch;
98
- let callCount = 0;
99
-
100
- globalThis.fetch = async (_url, _options) => {
101
- callCount++;
102
- throw new Error(`Persistent network failure ${callCount}`);
103
- };
104
-
105
- try {
106
- const content = `
107
- # Test Document
108
-
109
- \`\`\`javascript
110
- console.log("test");
111
- \`\`\`
112
- `;
113
-
114
- // Expect this to throw since all retries will fail
115
- await expect(evaluateDocumentCode({ content })).rejects.toThrow("Linting failed:");
116
-
117
- // Verify retries happened (should call 4 times total: 1 + 3 retries)
118
- expect(callCount).toBe(4);
119
- } finally {
120
- // Restore the original fetch function
121
- globalThis.fetch = originalFetch;
122
- }
123
- },
124
- 120 * 1000,
125
- );
126
-
127
- test("should demonstrate onFailedAttempt callback logic from lines 42-44", () => {
128
- // Test that simulates the exact logic from the onFailedAttempt callback (lines 42-44)
129
- // This verifies that the callback would format the debug message correctly
130
-
131
- // Simulate the parameters that would be passed to onFailedAttempt
132
- const mockFailedAttempt = {
133
- error: new Error("Simulated linter failure"),
134
- attemptNumber: 2,
135
- retriesLeft: 1,
136
- };
137
-
138
- // Simulate the exact logic from lines 43-44 in the source code
139
- const debugMessage = `Attempt ${mockFailedAttempt.attemptNumber} failed: ${mockFailedAttempt.error.message}. There are ${mockFailedAttempt.retriesLeft} retries left.`;
140
-
141
- // Verify the message format matches what's expected from the source
142
- const expectedMessage = "Attempt 2 failed: Simulated linter failure. There are 1 retries left.";
143
- expect(debugMessage).toBe(expectedMessage);
144
-
145
- // Verify the message format follows the pattern from lines 43-44
146
- const messagePattern = /Attempt \d+ failed: .+\. There are \d+ retries left\./;
147
- expect(debugMessage).toMatch(messagePattern);
148
-
149
- // Test with different retry scenarios
150
- const scenarios = [
151
- { attemptNumber: 1, retriesLeft: 2, error: new Error("First failure") },
152
- { attemptNumber: 3, retriesLeft: 0, error: new Error("Final attempt") },
153
- { attemptNumber: 2, retriesLeft: 1, error: new Error("Network timeout") },
154
- ];
155
-
156
- scenarios.forEach((scenario) => {
157
- const message = `Attempt ${scenario.attemptNumber} failed: ${scenario.error.message}. There are ${scenario.retriesLeft} retries left.`;
158
- expect(message).toMatch(messagePattern);
159
- expect(message).toContain(`Attempt ${scenario.attemptNumber} failed:`);
160
- expect(message).toContain(`There are ${scenario.retriesLeft} retries left.`);
161
- });
162
- });
163
- });
@@ -1,87 +0,0 @@
1
- # Services
2
-
3
- The `@blocklet/js-sdk` is organized into several service classes, each responsible for a specific domain of functionality. These services act as dedicated clients for different Blocklet API endpoints, providing a structured and intuitive way to interact with the platform's features.
4
-
5
- Most core services are pre-initialized and available as properties on the main `BlockletSDK` instance, which you can obtain using the `getBlockletSDK()` function.
6
-
7
- ```javascript Accessing a Service icon=logos:javascript
8
- import { getBlockletSDK } from '@blocklet/js-sdk';
9
-
10
- const sdk = getBlockletSDK();
11
-
12
- // Access the AuthService to get user info
13
- async function getUserProfile() {
14
- const profile = await sdk.user.getProfile();
15
- console.log(profile);
16
- }
17
-
18
- // Access the BlockletService to get blocklet info
19
- async function getBlockletMeta() {
20
- const meta = await sdk.blocklet.getMeta();
21
- console.log(meta);
22
- }
23
- ```
24
-
25
- The diagram below illustrates the structure of the `BlockletSDK` instance and its relationship with the core services.
26
-
27
- ```d2
28
- direction: down
29
-
30
- BlockletSDK: {
31
- label: "BlockletSDK Instance"
32
- shape: rectangle
33
-
34
- grid-columns: 3
35
- grid-gap: 50
36
-
37
- user: {
38
- label: "user: AuthService"
39
- shape: rectangle
40
- }
41
-
42
- blocklet: {
43
- label: "blocklet: BlockletService"
44
- shape: rectangle
45
- }
46
-
47
- userSession: {
48
- label: "userSession: UserSessionService"
49
- shape: rectangle
50
- }
51
-
52
- federated: {
53
- label: "federated: FederatedService"
54
- shape: rectangle
55
- }
56
-
57
- token: {
58
- label: "token: TokenService"
59
- shape: rectangle
60
- }
61
- }
62
- ```
63
-
64
- Below is a complete list of the available services. Click on any service to view its detailed API reference.
65
-
66
- <x-cards data-columns="2">
67
- <x-card data-title="AuthService" data-href="/api/services/auth" data-icon="lucide:user-cog">
68
- API for managing user profiles, privacy settings, notifications, and authentication actions like logout.
69
- </x-card>
70
- <x-card data-title="BlockletService" data-href="/api/services/blocklet" data-icon="lucide:box">
71
- API for fetching and loading blocklet metadata from `window.blocklet` or a remote URL.
72
- </x-card>
73
- <x-card data-title="ComponentService" data-href="/api/services/component" data-icon="lucide:layout-template">
74
- API for getting information about mounted components and constructing URLs for them.
75
- </x-card>
76
- <x-card data-title="FederatedService" data-href="/api/services/federated" data-icon="lucide:network">
77
- API for interacting with Federated Login Group settings and retrieving information about master and current apps.
78
- </x-card>
79
- <x-card data-title="TokenService" data-href="/api/services/token" data-icon="lucide:key-round">
80
- Low-level API for getting, setting, and removing session and refresh tokens from storage (Cookies and LocalStorage).
81
- </x-card>
82
- <x-card data-title="UserSessionService" data-href="/api/services/user-session" data-icon="lucide:users">
83
- API for fetching and managing user login sessions.
84
- </x-card>
85
- </x-cards>
86
-
87
- Each service provides a focused set of methods for a specific part of the Blocklet platform. To understand the data structures and types returned by these services, please see the [Types](./api-types.md) reference.
@@ -1,94 +0,0 @@
1
- # Getting Started
2
-
3
- This guide will walk you through the essential steps to install the `@blocklet/js-sdk` and make your first API call. Our goal is to get you up and running in just a few minutes.
4
-
5
- ## Installation
6
-
7
- First, you need to add the SDK to your project. You can use your preferred package manager:
8
-
9
- ```bash Installation icon=mdi:bash
10
- npm install @blocklet/js-sdk
11
-
12
- # or
13
-
14
- yarn add @blocklet/js-sdk
15
-
16
- # or
17
-
18
- pnpm add @blocklet/js-sdk
19
- ```
20
-
21
- ## Basic Usage
22
-
23
- The SDK is designed to be straightforward. The two most common use cases are accessing core Blocklet services (like user authentication) and making authenticated requests to your own Blocklet's backend.
24
-
25
- ### Accessing Core Services
26
-
27
- The easiest way to use the SDK is by importing the `getBlockletSDK` singleton factory. This function ensures that you always get the same SDK instance throughout your application, simplifying state management.
28
-
29
- Here's how you can use it to fetch the current user's profile:
30
-
31
- ```javascript Get User Profile icon=logos:javascript
32
- import { getBlockletSDK } from '@blocklet/js-sdk';
33
-
34
- const sdk = getBlockletSDK();
35
-
36
- async function fetchUserProfile() {
37
- try {
38
- const { data: userProfile } = await sdk.user.getProfile();
39
- console.log('User Profile:', userProfile);
40
- } catch (error) {
41
- console.error('Failed to fetch user profile:', error);
42
- }
43
- }
44
-
45
- fetchUserProfile();
46
- ```
47
-
48
- The `sdk` instance provides access to various services like `user`, `userSession`, `blocklet`, and more. These services handle communication with the well-known Blocklet service endpoints for you.
49
-
50
- ### Making API Requests to Your Blocklet
51
-
52
- For communicating with your own Blocklet's backend API, the SDK provides `createAxios` and `createFetch` helper functions. These are wrappers around Axios and the native Fetch API that come pre-configured with everything needed for authenticated requests.
53
-
54
- They automatically handle:
55
- - Setting the correct `baseURL` for your component.
56
- - Attaching the session token to the `Authorization` header.
57
- - Including the `x-csrf-token` for security.
58
- - Refreshing the session token automatically if it expires.
59
-
60
- Here’s how to create an API client for your backend using `createAxios`:
61
-
62
- ```javascript Create an API Client icon=logos:javascript
63
- import { createAxios } from '@blocklet/js-sdk';
64
-
65
- // Create an Axios instance configured for your Blocklet
66
- const apiClient = createAxios();
67
-
68
- async function fetchData() {
69
- try {
70
- // Make a request to your own backend, e.g., GET /api/posts
71
- const response = await apiClient.get('/api/posts');
72
- console.log('Posts:', response.data);
73
- } catch (error) {
74
- console.error('Failed to fetch data:', error);
75
- }
76
- }
77
-
78
- fetchData();
79
- ```
80
-
81
- With this setup, you don't need to manually manage tokens or headers. The SDK takes care of the authentication flow seamlessly.
82
-
83
- ## Next Steps
84
-
85
- You've now learned how to install the `@blocklet/js-sdk` and use it for the two most common scenarios. To dive deeper, we recommend exploring the following guides:
86
-
87
- <x-cards>
88
- <x-card data-title="Making API Requests" data-icon="lucide:file-code-2" data-href="/guides/making-api-requests">
89
- Learn more about advanced configuration for `createAxios` and `createFetch`, including error handling and request parameters.
90
- </x-card>
91
- <x-card data-title="Authentication" data-icon="lucide:key-round" data-href="/guides/authentication">
92
- Understand how the SDK manages session and refresh tokens under the hood to keep your users logged in.
93
- </x-card>
94
- </x-cards>
@@ -1,312 +0,0 @@
1
- import { afterAll, beforeAll, describe, expect, test } from "bun:test";
2
- import { existsSync } from "node:fs";
3
- import { mkdtemp, readFile, rm } from "node:fs/promises";
4
- import { tmpdir } from "node:os";
5
- import { join } from "node:path";
6
- import generateEvaluationReport from "../../../agents/evaluate/generate-report.mjs";
7
-
8
- describe("generateEvaluationReport", () => {
9
- let testDir;
10
-
11
- beforeAll(async () => {
12
- process.env.OBSERVABILITY_DISABLED = "true";
13
- // Create a temporary directory for testing
14
- testDir = await mkdtemp(join(tmpdir(), "test-evaluation-report-"));
15
- });
16
-
17
- afterAll(async () => {
18
- delete process.env.OBSERVABILITY_DISABLED;
19
-
20
- // Clean up test files
21
- try {
22
- if (existsSync(testDir)) {
23
- await rm(testDir, { recursive: true, force: true });
24
- }
25
- } catch (error) {
26
- console.warn("Failed to clean up test files:", error.message);
27
- }
28
- });
29
-
30
- test("should generate evaluation report with correct structure", async () => {
31
- // Mock evaluation data matching the expected schema
32
- const testData = {
33
- structureEvaluation: {
34
- purposeCoverage: {
35
- score: 4,
36
- reason: "Covers most main objectives, missing minor targets",
37
- covered: ["Quick Start", "API Reference"],
38
- missing: ["Troubleshooting"],
39
- },
40
- audienceCoverage: {
41
- score: 5,
42
- reason: "Covers all selected audiences",
43
- covered: ["Developers", "DevOps Engineers"],
44
- missing: [],
45
- },
46
- coverageDepthAlignment: {
47
- score: 3,
48
- reason: "About half of modules depth does not match expectations",
49
- },
50
- },
51
- originalDocumentStructure: [
52
- {
53
- path: "/api/authentication",
54
- title: "Authentication",
55
- description: "Authentication guide",
56
- parentId: null,
57
- documentEvaluation: {
58
- readability: {
59
- score: 4,
60
- reason: "Clear language with minor errors that don't affect reading",
61
- },
62
- coherence: { score: 5, reason: "Clear logic, no contradictions or jumps" },
63
- contentQuality: { score: 3, reason: "50-70% implementation, some content is brief" },
64
- translationQuality: { score: 4, reason: "Generally accurate with minor issues" },
65
- consistency: { score: 4, reason: "Generally consistent with 1-2 differences" },
66
- purposeAlignment: {
67
- score: 4,
68
- reason: "Generally meets objectives with minor irrelevant content",
69
- },
70
- audienceAlignment: { score: 5, reason: "Completely meets audience needs" },
71
- knowledgeLevelAlignment: { score: 3, reason: "Partial match, about half doesn't fit" },
72
- },
73
- codeEvaluation: null,
74
- },
75
- {
76
- path: "/api/endpoints",
77
- title: "API Endpoints",
78
- description: "API endpoints documentation",
79
- parentId: null,
80
- documentEvaluation: {
81
- readability: { score: 5, reason: "No errors, natural and fluent language" },
82
- coherence: {
83
- score: 4,
84
- reason: "Overall coherent with occasional unnatural transitions",
85
- },
86
- contentQuality: {
87
- score: 4,
88
- reason: "70-90% planning points implemented, minor details lacking",
89
- },
90
- translationQuality: {
91
- score: 5,
92
- reason: "Accurate and natural, consistent terminology",
93
- },
94
- consistency: { score: 5, reason: "Completely consistent" },
95
- purposeAlignment: { score: 5, reason: "Completely meets objectives, closely related" },
96
- audienceAlignment: { score: 4, reason: "Generally fits with minor mismatches" },
97
- knowledgeLevelAlignment: {
98
- score: 4,
99
- reason: "Mostly matches, slightly too shallow/deep in places",
100
- },
101
- },
102
- codeEvaluation: null,
103
- },
104
- ],
105
- metadata: {
106
- documentTitle: "API Usage Guide",
107
- evaluator: "test-suite",
108
- },
109
- basePath: testDir,
110
- projectName: "Test Project",
111
- projectDesc: "A test project for evaluation",
112
- projectLogo: "test-logo.png",
113
- documentPurpose: "Provide API documentation",
114
- targetAudienceTypes: ["Developers", "DevOps Engineers"],
115
- readerKnowledgeLevel: "Intermediate",
116
- documentationDepth: "Comprehensive",
117
- targetAudience: "Software developers and engineers",
118
- };
119
-
120
- // Call the function
121
- const result = await generateEvaluationReport(testData);
122
-
123
- // Verify result structure
124
- expect(result).toBeDefined();
125
- expect(result.message).toBeDefined();
126
- expect(result.message).toContain("integrity-report.json");
127
- expect(result.message).toContain("doc-smith/evaluate/");
128
-
129
- // Extract report path from result message
130
- const reportPathMatch = result.message.match(/`([^`]+\.json)`/);
131
- expect(reportPathMatch).toBeTruthy();
132
- const reportPath = reportPathMatch[1];
133
-
134
- // Verify file was created
135
- expect(existsSync(reportPath)).toBe(true);
136
-
137
- // Read and parse the report
138
- const reportContent = await readFile(reportPath, "utf8");
139
- const report = JSON.parse(reportContent);
140
-
141
- // Verify report structure
142
- expect(report).toBeDefined();
143
- expect(report.documentInfo).toBeDefined();
144
- expect(report.metadata).toBeDefined();
145
- expect(report.structureEvaluation).toBeDefined();
146
- expect(report.documentEvaluations).toBeDefined();
147
-
148
- // Verify document info
149
- expect(report.documentInfo.projectName).toBe("Test Project");
150
- expect(report.documentInfo.projectDesc).toBe("A test project for evaluation");
151
- expect(report.documentInfo.projectLogo).toBe("test-logo.png");
152
- expect(report.documentInfo.documentPurpose).toBe("Provide API documentation");
153
- expect(report.documentInfo.targetAudienceTypes).toEqual(["Developers", "DevOps Engineers"]);
154
- expect(report.documentInfo.readerKnowledgeLevel).toBe("Intermediate");
155
- expect(report.documentInfo.documentationDepth).toBe("Comprehensive");
156
- expect(report.documentInfo.targetAudience).toBe("Software developers and engineers");
157
-
158
- // Verify metadata
159
- expect(report.metadata.version).toBe("0.1.0");
160
- expect(report.metadata.generatedBy).toBe("AIGNE Doc Smith");
161
- expect(report.metadata.generatedAt).toBeDefined();
162
- expect(report.metadata.documentCount).toBe(2);
163
- expect(report.metadata.documentTitle).toBe("API Usage Guide");
164
- expect(report.metadata.evaluator).toBe("test-suite");
165
-
166
- // Verify structure evaluation
167
- expect(report.structureEvaluation.type).toBe("document-structure");
168
- expect(report.structureEvaluation.results.purposeCoverage).toEqual(
169
- testData.structureEvaluation.purposeCoverage,
170
- );
171
- expect(report.structureEvaluation.results.audienceCoverage).toEqual(
172
- testData.structureEvaluation.audienceCoverage,
173
- );
174
- expect(report.structureEvaluation.results.coverageDepthAlignment).toEqual(
175
- testData.structureEvaluation.coverageDepthAlignment,
176
- );
177
-
178
- // Verify document evaluations
179
- expect(report.documentEvaluations.type).toBe("document-content");
180
- expect(report.documentEvaluations.results).toHaveLength(2);
181
-
182
- // Verify individual document evaluations
183
- const firstDoc = report.documentEvaluations.results[0];
184
- expect(firstDoc.path).toBe("/api/authentication");
185
- expect(firstDoc.title).toBe("Authentication");
186
- expect(firstDoc.description).toBe("Authentication guide");
187
- expect(firstDoc.parentId).toBe(null);
188
- expect(firstDoc.documentEvaluation.readability.score).toBe(4);
189
- expect(firstDoc.codeEvaluation).toBe(null);
190
- });
191
-
192
- test("should handle empty documentation structure", async () => {
193
- const testData = {
194
- structureEvaluation: {
195
- purposeCoverage: {
196
- score: 5,
197
- reason: "Completely covers all objectives",
198
- covered: ["Objective 1", "Objective 2"],
199
- missing: [],
200
- },
201
- audienceCoverage: {
202
- score: 5,
203
- reason: "Completely covers all audiences",
204
- covered: ["Audience 1", "Audience 2"],
205
- missing: [],
206
- },
207
- coverageDepthAlignment: {
208
- score: 5,
209
- reason: "Depth completely matches expectations",
210
- },
211
- },
212
- originalDocumentStructure: [],
213
- metadata: {
214
- documentTitle: "Test Document",
215
- },
216
- basePath: testDir,
217
- projectName: "Empty Test Project",
218
- projectDesc: "Test project with no documents",
219
- projectLogo: "empty-logo.png",
220
- documentPurpose: "Test empty structure",
221
- targetAudienceTypes: ["Testers"],
222
- readerKnowledgeLevel: "Beginner",
223
- documentationDepth: "Basic",
224
- targetAudience: "Test users",
225
- };
226
-
227
- const result = await generateEvaluationReport(testData);
228
-
229
- expect(result).toBeDefined();
230
- expect(result.message).toBeDefined();
231
-
232
- // Extract report path from result message
233
- const reportPathMatch = result.message.match(/`([^`]+\.json)`/);
234
- expect(reportPathMatch).toBeTruthy();
235
- const reportPath = reportPathMatch[1];
236
-
237
- expect(existsSync(reportPath)).toBe(true);
238
-
239
- const reportContent = await readFile(reportPath, "utf8");
240
- const report = JSON.parse(reportContent);
241
-
242
- expect(report.metadata.documentCount).toBe(0);
243
- expect(report.documentEvaluations.results).toHaveLength(0);
244
- });
245
-
246
- test("should handle missing optional parameters", async () => {
247
- const testData = {
248
- structureEvaluation: {
249
- purposeCoverage: {
250
- score: 3,
251
- reason: "Partial coverage",
252
- },
253
- audienceCoverage: {
254
- score: 3,
255
- reason: "Partial coverage",
256
- },
257
- coverageDepthAlignment: {
258
- score: 3,
259
- reason: "Generally compliant",
260
- },
261
- },
262
- originalDocumentStructure: [
263
- {
264
- path: "/test",
265
- title: "Test Document",
266
- description: "Test document description",
267
- parentId: null,
268
- documentEvaluation: {
269
- readability: { score: 3, reason: "Fair" },
270
- coherence: { score: 3, reason: "Fair" },
271
- contentQuality: { score: 3, reason: "Fair" },
272
- translationQuality: { score: 3, reason: "Fair" },
273
- consistency: { score: 3, reason: "Fair" },
274
- purposeAlignment: { score: 3, reason: "Fair" },
275
- audienceAlignment: { score: 3, reason: "Fair" },
276
- knowledgeLevelAlignment: { score: 3, reason: "Fair" },
277
- },
278
- codeEvaluation: null,
279
- },
280
- ],
281
- basePath: testDir,
282
- projectName: "Minimal Test Project",
283
- projectDesc: "Minimal test setup",
284
- projectLogo: "minimal-logo.png",
285
- documentPurpose: "Test minimal configuration",
286
- targetAudienceTypes: ["General Users"],
287
- readerKnowledgeLevel: "Basic",
288
- documentationDepth: "Minimal",
289
- targetAudience: "General audience",
290
- // metadata is optional
291
- };
292
-
293
- const result = await generateEvaluationReport(testData);
294
-
295
- expect(result).toBeDefined();
296
- expect(result.message).toBeDefined();
297
-
298
- // Extract report path from result message
299
- const reportPathMatch = result.message.match(/`([^`]+\.json)`/);
300
- expect(reportPathMatch).toBeTruthy();
301
- const reportPath = reportPathMatch[1];
302
-
303
- expect(existsSync(reportPath)).toBe(true);
304
-
305
- const reportContent = await readFile(reportPath, "utf8");
306
- const report = JSON.parse(reportContent);
307
-
308
- expect(report.metadata.version).toBe("0.1.0");
309
- expect(report.metadata.generatedBy).toBe("AIGNE Doc Smith");
310
- expect(report.metadata.documentCount).toBe(1);
311
- });
312
- });