@anydocs/core 1.0.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 (124) hide show
  1. package/dist/config/index.d.ts +2 -0
  2. package/dist/config/index.d.ts.map +1 -0
  3. package/dist/config/index.js +1 -0
  4. package/dist/config/project-config.d.ts +10 -0
  5. package/dist/config/project-config.d.ts.map +1 -0
  6. package/dist/config/project-config.js +52 -0
  7. package/dist/errors/domain-error.d.ts +12 -0
  8. package/dist/errors/domain-error.d.ts.map +1 -0
  9. package/dist/errors/domain-error.js +8 -0
  10. package/dist/errors/index.d.ts +3 -0
  11. package/dist/errors/index.d.ts.map +1 -0
  12. package/dist/errors/index.js +2 -0
  13. package/dist/errors/validation-error.d.ts +5 -0
  14. package/dist/errors/validation-error.d.ts.map +1 -0
  15. package/dist/errors/validation-error.js +7 -0
  16. package/dist/fs/api-source-repository.d.ts +16 -0
  17. package/dist/fs/api-source-repository.d.ts.map +1 -0
  18. package/dist/fs/api-source-repository.js +89 -0
  19. package/dist/fs/content-repository.d.ts +13 -0
  20. package/dist/fs/content-repository.d.ts.map +1 -0
  21. package/dist/fs/content-repository.js +171 -0
  22. package/dist/fs/docs-repository.d.ts +26 -0
  23. package/dist/fs/docs-repository.d.ts.map +1 -0
  24. package/dist/fs/docs-repository.js +270 -0
  25. package/dist/fs/index.d.ts +5 -0
  26. package/dist/fs/index.d.ts.map +1 -0
  27. package/dist/fs/index.js +4 -0
  28. package/dist/fs/project-paths.d.ts +4 -0
  29. package/dist/fs/project-paths.d.ts.map +1 -0
  30. package/dist/fs/project-paths.js +55 -0
  31. package/dist/index.d.ts +9 -0
  32. package/dist/index.d.ts.map +1 -0
  33. package/dist/index.js +8 -0
  34. package/dist/publishing/build-artifacts.d.ts +4 -0
  35. package/dist/publishing/build-artifacts.d.ts.map +1 -0
  36. package/dist/publishing/build-artifacts.js +453 -0
  37. package/dist/publishing/build-openapi-artifacts.d.ts +3 -0
  38. package/dist/publishing/build-openapi-artifacts.d.ts.map +1 -0
  39. package/dist/publishing/build-openapi-artifacts.js +253 -0
  40. package/dist/publishing/index.d.ts +4 -0
  41. package/dist/publishing/index.d.ts.map +1 -0
  42. package/dist/publishing/index.js +3 -0
  43. package/dist/publishing/publication-filter.d.ts +22 -0
  44. package/dist/publishing/publication-filter.d.ts.map +1 -0
  45. package/dist/publishing/publication-filter.js +98 -0
  46. package/dist/schemas/api-source-schema.d.ts +3 -0
  47. package/dist/schemas/api-source-schema.d.ts.map +1 -0
  48. package/dist/schemas/api-source-schema.js +110 -0
  49. package/dist/schemas/docs-schema.d.ts +7 -0
  50. package/dist/schemas/docs-schema.d.ts.map +1 -0
  51. package/dist/schemas/docs-schema.js +212 -0
  52. package/dist/schemas/index.d.ts +4 -0
  53. package/dist/schemas/index.d.ts.map +1 -0
  54. package/dist/schemas/index.js +3 -0
  55. package/dist/schemas/project-schema.d.ts +3 -0
  56. package/dist/schemas/project-schema.d.ts.map +1 -0
  57. package/dist/schemas/project-schema.js +268 -0
  58. package/dist/services/authoring-service.d.ts +137 -0
  59. package/dist/services/authoring-service.d.ts.map +1 -0
  60. package/dist/services/authoring-service.js +583 -0
  61. package/dist/services/build-service.d.ts +35 -0
  62. package/dist/services/build-service.d.ts.map +1 -0
  63. package/dist/services/build-service.js +84 -0
  64. package/dist/services/index.d.ts +11 -0
  65. package/dist/services/index.d.ts.map +1 -0
  66. package/dist/services/index.js +10 -0
  67. package/dist/services/init-service.d.ts +15 -0
  68. package/dist/services/init-service.d.ts.map +1 -0
  69. package/dist/services/init-service.js +127 -0
  70. package/dist/services/legacy-conversion-service.d.ts +8 -0
  71. package/dist/services/legacy-conversion-service.d.ts.map +1 -0
  72. package/dist/services/legacy-conversion-service.js +601 -0
  73. package/dist/services/legacy-import-service.d.ts +10 -0
  74. package/dist/services/legacy-import-service.d.ts.map +1 -0
  75. package/dist/services/legacy-import-service.js +239 -0
  76. package/dist/services/page-template-service.d.ts +81 -0
  77. package/dist/services/page-template-service.d.ts.map +1 -0
  78. package/dist/services/page-template-service.js +342 -0
  79. package/dist/services/preview-service.d.ts +29 -0
  80. package/dist/services/preview-service.d.ts.map +1 -0
  81. package/dist/services/preview-service.js +45 -0
  82. package/dist/services/watch-service.d.ts +24 -0
  83. package/dist/services/watch-service.d.ts.map +1 -0
  84. package/dist/services/watch-service.js +216 -0
  85. package/dist/services/web-runtime-bridge.d.ts +33 -0
  86. package/dist/services/web-runtime-bridge.d.ts.map +1 -0
  87. package/dist/services/web-runtime-bridge.js +330 -0
  88. package/dist/services/workflow-compatibility-service.d.ts +3 -0
  89. package/dist/services/workflow-compatibility-service.d.ts.map +1 -0
  90. package/dist/services/workflow-compatibility-service.js +53 -0
  91. package/dist/services/workflow-standard-service.d.ts +9 -0
  92. package/dist/services/workflow-standard-service.d.ts.map +1 -0
  93. package/dist/services/workflow-standard-service.js +372 -0
  94. package/dist/types/api-source.d.ts +34 -0
  95. package/dist/types/api-source.d.ts.map +1 -0
  96. package/dist/types/api-source.js +8 -0
  97. package/dist/types/docs.d.ts +65 -0
  98. package/dist/types/docs.d.ts.map +1 -0
  99. package/dist/types/docs.js +8 -0
  100. package/dist/types/index.d.ts +6 -0
  101. package/dist/types/index.d.ts.map +1 -0
  102. package/dist/types/index.js +5 -0
  103. package/dist/types/legacy-import.d.ts +72 -0
  104. package/dist/types/legacy-import.d.ts.map +1 -0
  105. package/dist/types/legacy-import.js +1 -0
  106. package/dist/types/project.d.ts +85 -0
  107. package/dist/types/project.d.ts.map +1 -0
  108. package/dist/types/project.js +5 -0
  109. package/dist/types/workflow-standard.d.ts +51 -0
  110. package/dist/types/workflow-standard.d.ts.map +1 -0
  111. package/dist/types/workflow-standard.js +1 -0
  112. package/dist/utils/index.d.ts +4 -0
  113. package/dist/utils/index.d.ts.map +1 -0
  114. package/dist/utils/index.js +3 -0
  115. package/dist/utils/slug.d.ts +3 -0
  116. package/dist/utils/slug.d.ts.map +1 -0
  117. package/dist/utils/slug.js +21 -0
  118. package/dist/utils/yoopta-content.d.ts +13 -0
  119. package/dist/utils/yoopta-content.d.ts.map +1 -0
  120. package/dist/utils/yoopta-content.js +73 -0
  121. package/dist/utils/yoopta-render.d.ts +7 -0
  122. package/dist/utils/yoopta-render.d.ts.map +1 -0
  123. package/dist/utils/yoopta-render.js +155 -0
  124. package/package.json +30 -0
@@ -0,0 +1,212 @@
1
+ import { isDocsLang, isPageStatus, } from "../types/docs.js";
2
+ import { ValidationError } from "../errors/validation-error.js";
3
+ function isRecord(value) {
4
+ return typeof value === 'object' && value !== null && !Array.isArray(value);
5
+ }
6
+ function createDocsValidationError(entity, rule, remediation, metadata) {
7
+ return new ValidationError(`Validation failed for "${entity}" on rule "${rule}".`, {
8
+ entity,
9
+ rule,
10
+ remediation,
11
+ metadata,
12
+ });
13
+ }
14
+ function assertNonEmptyString(value, entity, rule, remediation) {
15
+ if (typeof value !== 'string' || value.trim().length === 0) {
16
+ throw createDocsValidationError(entity, rule, remediation, { received: value });
17
+ }
18
+ }
19
+ function assertOptionalStringArray(value, entity, rule, remediation) {
20
+ if (value == null) {
21
+ return;
22
+ }
23
+ if (!Array.isArray(value) || value.some((item) => typeof item !== 'string')) {
24
+ throw createDocsValidationError(entity, rule, remediation, { received: value });
25
+ }
26
+ }
27
+ function assertOptionalNavGroupId(value, pathLabel) {
28
+ if (value == null) {
29
+ return undefined;
30
+ }
31
+ if (typeof value !== 'string' || value.trim().length === 0) {
32
+ throw createDocsValidationError('nav-item', 'group-id-string', 'Use a non-empty string for "id" on navigation groups when a stable group id is needed.', { path: pathLabel, received: value });
33
+ }
34
+ const trimmed = value.trim();
35
+ if (!/^[a-z0-9]+(?:-[a-z0-9]+)*$/.test(trimmed)) {
36
+ throw createDocsValidationError('nav-item', 'group-id-format', 'Use lowercase letters, numbers, and hyphens only for navigation group ids.', { path: pathLabel, received: value });
37
+ }
38
+ return trimmed;
39
+ }
40
+ function validateNavItem(input, pathLabel) {
41
+ if (!isRecord(input) || typeof input.type !== 'string') {
42
+ throw createDocsValidationError('nav-item', 'nav-item-structure', 'Ensure each navigation item is an object with a valid "type" field.', { path: pathLabel, received: input });
43
+ }
44
+ switch (input.type) {
45
+ case 'section':
46
+ case 'folder': {
47
+ assertNonEmptyString(input.title, 'nav-item', 'group-title-required', 'Provide a non-empty "title" for section and folder navigation items.');
48
+ if (!Array.isArray(input.children)) {
49
+ throw createDocsValidationError('nav-item', 'group-children-required', 'Provide a "children" array for section and folder navigation items.', { path: pathLabel, received: input.children });
50
+ }
51
+ return {
52
+ type: input.type,
53
+ ...(assertOptionalNavGroupId(input.id, pathLabel) ? { id: assertOptionalNavGroupId(input.id, pathLabel) } : {}),
54
+ title: input.title.trim(),
55
+ children: input.children.map((child, index) => validateNavItem(child, `${pathLabel}.children[${index}]`)),
56
+ };
57
+ }
58
+ case 'page': {
59
+ assertNonEmptyString(input.pageId, 'nav-item', 'page-id-required', 'Provide a non-empty "pageId" for page navigation items.');
60
+ if (input.titleOverride != null && typeof input.titleOverride !== 'string') {
61
+ throw createDocsValidationError('nav-item', 'title-override-string', 'Use a string for "titleOverride" when overriding a page title.', { path: pathLabel, received: input.titleOverride });
62
+ }
63
+ if (input.hidden != null && typeof input.hidden !== 'boolean') {
64
+ throw createDocsValidationError('nav-item', 'hidden-boolean', 'Use a boolean for "hidden" on page navigation items.', { path: pathLabel, received: input.hidden });
65
+ }
66
+ return {
67
+ type: 'page',
68
+ pageId: input.pageId.trim(),
69
+ ...(input.titleOverride ? { titleOverride: input.titleOverride } : {}),
70
+ ...(typeof input.hidden === 'boolean' ? { hidden: input.hidden } : {}),
71
+ };
72
+ }
73
+ case 'link': {
74
+ assertNonEmptyString(input.title, 'nav-item', 'link-title-required', 'Provide a non-empty "title" for link navigation items.');
75
+ assertNonEmptyString(input.href, 'nav-item', 'link-href-required', 'Provide a non-empty "href" for link navigation items.');
76
+ return {
77
+ type: 'link',
78
+ title: input.title.trim(),
79
+ href: input.href.trim(),
80
+ };
81
+ }
82
+ default:
83
+ throw createDocsValidationError('nav-item', 'unsupported-nav-item-type', 'Use only section, folder, page, or link navigation item types.', { path: pathLabel, received: input.type });
84
+ }
85
+ }
86
+ function validateReviewWarning(input, index) {
87
+ if (!isRecord(input)) {
88
+ throw createDocsValidationError('page-review-warning', 'page-review-warning-object', 'Use an object for each page review warning entry.', { index, received: input });
89
+ }
90
+ assertNonEmptyString(input.code, 'page-review-warning', 'page-review-warning-code-required', 'Provide a non-empty code for each review warning.');
91
+ assertNonEmptyString(input.message, 'page-review-warning', 'page-review-warning-message-required', 'Provide a non-empty message for each review warning.');
92
+ if (input.remediation != null && typeof input.remediation !== 'string') {
93
+ throw createDocsValidationError('page-review-warning', 'page-review-warning-remediation-string', 'Use a string remediation when a review warning includes remediation guidance.', { index, received: input.remediation });
94
+ }
95
+ if (input.metadata != null && !isRecord(input.metadata)) {
96
+ throw createDocsValidationError('page-review-warning', 'page-review-warning-metadata-object', 'Use an object for review warning metadata when it is present.', { index, received: input.metadata });
97
+ }
98
+ return {
99
+ code: input.code.trim(),
100
+ message: input.message.trim(),
101
+ ...(typeof input.remediation === 'string' ? { remediation: input.remediation } : {}),
102
+ ...(isRecord(input.metadata) ? { metadata: input.metadata } : {}),
103
+ };
104
+ }
105
+ function validatePageReview(input) {
106
+ if (!isRecord(input)) {
107
+ throw createDocsValidationError('page-review', 'page-review-object', 'Use an object for page review metadata when review metadata is present.', { received: input });
108
+ }
109
+ if (typeof input.required !== 'boolean') {
110
+ throw createDocsValidationError('page-review', 'page-review-required-boolean', 'Provide a boolean "required" field on page review metadata.', { received: input.required });
111
+ }
112
+ if (input.sourceType !== 'legacy-import' && input.sourceType !== 'ai-generated') {
113
+ throw createDocsValidationError('page-review', 'page-review-source-type', 'Use "legacy-import" or "ai-generated" for page review sourceType.', { received: input.sourceType });
114
+ }
115
+ assertNonEmptyString(input.sourceId, 'page-review', 'page-review-source-id-required', 'Provide a non-empty sourceId for page review metadata.');
116
+ if (input.itemId != null && typeof input.itemId !== 'string') {
117
+ throw createDocsValidationError('page-review', 'page-review-item-id-string', 'Use a string itemId when page review metadata includes an itemId.', { received: input.itemId });
118
+ }
119
+ if (input.sourcePath != null && typeof input.sourcePath !== 'string') {
120
+ throw createDocsValidationError('page-review', 'page-review-source-path-string', 'Use a string sourcePath when page review metadata includes a sourcePath.', { received: input.sourcePath });
121
+ }
122
+ if (input.approvedAt != null && typeof input.approvedAt !== 'string') {
123
+ throw createDocsValidationError('page-review', 'page-review-approved-at-string', 'Use an ISO 8601 string for approvedAt when review approval metadata is present.', { received: input.approvedAt });
124
+ }
125
+ if (input.metadata != null && !isRecord(input.metadata)) {
126
+ throw createDocsValidationError('page-review', 'page-review-metadata-object', 'Use an object for page review metadata.metadata when present.', { received: input.metadata });
127
+ }
128
+ if (input.warnings != null && !Array.isArray(input.warnings)) {
129
+ throw createDocsValidationError('page-review', 'page-review-warnings-array', 'Use an array for page review warnings when present.', { received: input.warnings });
130
+ }
131
+ return {
132
+ required: input.required,
133
+ sourceType: input.sourceType,
134
+ sourceId: input.sourceId.trim(),
135
+ ...(typeof input.itemId === 'string' ? { itemId: input.itemId } : {}),
136
+ ...(typeof input.sourcePath === 'string' ? { sourcePath: input.sourcePath } : {}),
137
+ ...(typeof input.approvedAt === 'string' ? { approvedAt: input.approvedAt } : {}),
138
+ ...(isRecord(input.metadata) ? { metadata: input.metadata } : {}),
139
+ ...(Array.isArray(input.warnings)
140
+ ? { warnings: input.warnings.map((warning, index) => validateReviewWarning(warning, index)) }
141
+ : {}),
142
+ };
143
+ }
144
+ export function validateNavigationDoc(input) {
145
+ if (!isRecord(input)) {
146
+ throw createDocsValidationError('navigation-doc', 'navigation-doc-must-be-object', 'Ensure the navigation file is a JSON object.');
147
+ }
148
+ if (typeof input.version !== 'number') {
149
+ throw createDocsValidationError('navigation-doc', 'navigation-version-required', 'Provide a numeric "version" on the navigation document.', { received: input.version });
150
+ }
151
+ if (!Array.isArray(input.items)) {
152
+ throw createDocsValidationError('navigation-doc', 'navigation-items-required', 'Provide an "items" array on the navigation document.', { received: input.items });
153
+ }
154
+ return {
155
+ version: input.version,
156
+ items: input.items.map((item, index) => validateNavItem(item, `items[${index}]`)),
157
+ };
158
+ }
159
+ export function validatePageDoc(input, options = {}) {
160
+ if (!isRecord(input)) {
161
+ throw createDocsValidationError('page-doc', 'page-doc-must-be-object', 'Ensure the page document is a JSON object.');
162
+ }
163
+ assertNonEmptyString(input.id, 'page-doc', 'page-id-required', 'Provide a non-empty "id" for the page.');
164
+ if (!isDocsLang(input.lang)) {
165
+ throw createDocsValidationError('page-doc', 'page-language-invalid', 'Use a supported docs language such as "en" or "zh".', { received: input.lang });
166
+ }
167
+ assertNonEmptyString(input.slug, 'page-doc', 'page-slug-required', 'Provide a non-empty "slug" for the page.');
168
+ assertNonEmptyString(input.title, 'page-doc', 'page-title-required', 'Provide a non-empty "title" for the page.');
169
+ if (input.description != null && typeof input.description !== 'string') {
170
+ throw createDocsValidationError('page-doc', 'page-description-string', 'Use a string for "description" when the field is present.', { received: input.description });
171
+ }
172
+ assertOptionalStringArray(input.tags, 'page-doc', 'page-tags-string-array', 'Use a string array for "tags" when tags are present.');
173
+ if (!isPageStatus(input.status)) {
174
+ throw createDocsValidationError('page-doc', 'page-status-invalid', 'Use one of the supported page statuses: draft, in_review, published.', { received: input.status });
175
+ }
176
+ if (input.updatedAt != null && typeof input.updatedAt !== 'string') {
177
+ throw createDocsValidationError('page-doc', 'page-updated-at-string', 'Use an ISO 8601 string for "updatedAt" when the field is present.', { received: input.updatedAt });
178
+ }
179
+ if (input.render != null) {
180
+ if (!isRecord(input.render)) {
181
+ throw createDocsValidationError('page-doc', 'page-render-must-be-object', 'Use an object for "render" when render metadata is present.', { received: input.render });
182
+ }
183
+ if (input.render.markdown != null && typeof input.render.markdown !== 'string') {
184
+ throw createDocsValidationError('page-doc', 'page-render-markdown-string', 'Use a string for render.markdown when present.', { received: input.render.markdown });
185
+ }
186
+ if (input.render.plainText != null && typeof input.render.plainText !== 'string') {
187
+ throw createDocsValidationError('page-doc', 'page-render-plain-text-string', 'Use a string for render.plainText when present.', { received: input.render.plainText });
188
+ }
189
+ }
190
+ if (!('content' in input)) {
191
+ throw createDocsValidationError('page-doc', 'page-content-required', 'Provide a "content" payload for the page document.');
192
+ }
193
+ if (options.validateContent) {
194
+ options.validateContent(input.content);
195
+ }
196
+ if (input.review != null && !isRecord(input.review)) {
197
+ throw createDocsValidationError('page-doc', 'page-review-object', 'Use an object for page review metadata when the review field is present.', { received: input.review });
198
+ }
199
+ return {
200
+ id: input.id.trim(),
201
+ lang: input.lang,
202
+ slug: input.slug.trim(),
203
+ title: input.title.trim(),
204
+ ...(typeof input.description === 'string' ? { description: input.description } : {}),
205
+ ...(Array.isArray(input.tags) ? { tags: input.tags } : {}),
206
+ status: input.status,
207
+ ...(typeof input.updatedAt === 'string' ? { updatedAt: input.updatedAt } : {}),
208
+ content: input.content,
209
+ ...(isRecord(input.render) ? { render: input.render } : {}),
210
+ ...(isRecord(input.review) ? { review: validatePageReview(input.review) } : {}),
211
+ };
212
+ }
@@ -0,0 +1,4 @@
1
+ export * from './api-source-schema.ts';
2
+ export * from './docs-schema.ts';
3
+ export * from './project-schema.ts';
4
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/schemas/index.ts"],"names":[],"mappings":"AAAA,cAAc,wBAAwB,CAAC;AACvC,cAAc,kBAAkB,CAAC;AACjC,cAAc,qBAAqB,CAAC"}
@@ -0,0 +1,3 @@
1
+ export * from "./api-source-schema.js";
2
+ export * from "./docs-schema.js";
3
+ export * from "./project-schema.js";
@@ -0,0 +1,3 @@
1
+ import { type ProjectConfig } from '../types/project.ts';
2
+ export declare function validateProjectConfig(input: unknown): ProjectConfig;
3
+ //# sourceMappingURL=project-schema.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"project-schema.d.ts","sourceRoot":"","sources":["../../src/schemas/project-schema.ts"],"names":[],"mappings":"AACA,OAAO,EAOL,KAAK,aAAa,EACnB,MAAM,qBAAqB,CAAC;AAyJ7B,wBAAgB,qBAAqB,CAAC,KAAK,EAAE,OAAO,GAAG,aAAa,CAmUnE"}
@@ -0,0 +1,268 @@
1
+ import { ValidationError } from "../errors/validation-error.js";
2
+ import { SUPPORTED_DOCS_CODE_THEMES, SUPPORTED_DOCS_LANGUAGES, } from "../types/project.js";
3
+ function isRecord(value) {
4
+ return typeof value === 'object' && value !== null && !Array.isArray(value);
5
+ }
6
+ function isSupportedLanguage(value) {
7
+ return typeof value === 'string' && SUPPORTED_DOCS_LANGUAGES.includes(value);
8
+ }
9
+ function makeValidationError(rule, remediation, metadata) {
10
+ return new ValidationError(`Project configuration failed validation for rule "${rule}".`, {
11
+ entity: 'project-config',
12
+ rule,
13
+ remediation,
14
+ metadata,
15
+ });
16
+ }
17
+ function isHexColor(value) {
18
+ return /^#[0-9a-fA-F]{6}$/.test(value);
19
+ }
20
+ function isSlugLikeId(value) {
21
+ return /^[a-z0-9]+(?:-[a-z0-9]+)*$/.test(value);
22
+ }
23
+ function validateTopNavLabel(input, itemId) {
24
+ if (typeof input === 'string') {
25
+ if (input.trim().length === 0) {
26
+ throw makeValidationError('site-navigation-top-nav-label-string', 'Use a non-empty string for a top navigation label.', { itemId, received: input });
27
+ }
28
+ return input.trim();
29
+ }
30
+ if (!isRecord(input)) {
31
+ throw makeValidationError('site-navigation-top-nav-label-object', 'Use a string or language-keyed object for top navigation labels.', { itemId, received: input });
32
+ }
33
+ const next = {};
34
+ for (const language of SUPPORTED_DOCS_LANGUAGES) {
35
+ const value = input[language];
36
+ if (value == null) {
37
+ continue;
38
+ }
39
+ if (typeof value !== 'string' || value.trim().length === 0) {
40
+ throw makeValidationError('site-navigation-top-nav-label-language-string', `Use a non-empty string for "site.navigation.topNav[].label.${language}" when provided.`, { itemId, language, received: value });
41
+ }
42
+ next[language] = value.trim();
43
+ }
44
+ if (Object.keys(next).length === 0) {
45
+ throw makeValidationError('site-navigation-top-nav-label-language-required', 'Provide at least one localized top navigation label value.', { itemId, received: input });
46
+ }
47
+ return next;
48
+ }
49
+ function validateTopNavItem(input, index) {
50
+ if (!isRecord(input)) {
51
+ throw makeValidationError('site-navigation-top-nav-item-object', 'Use an object for each top navigation item.', { index, received: input });
52
+ }
53
+ const id = input.id;
54
+ if (typeof id !== 'string' || id.trim().length === 0 || !isSlugLikeId(id.trim())) {
55
+ throw makeValidationError('site-navigation-top-nav-item-id', 'Use a lowercase slug-like id for each top navigation item.', { index, received: id });
56
+ }
57
+ if (input.type !== 'nav-group' && input.type !== 'external') {
58
+ throw makeValidationError('site-navigation-top-nav-item-type', 'Use "nav-group" or "external" for each top navigation item type.', { index, itemId: id.trim(), received: input.type });
59
+ }
60
+ const label = validateTopNavLabel(input.label, id.trim());
61
+ if (input.type === 'nav-group') {
62
+ const groupId = input.groupId;
63
+ if (typeof groupId !== 'string' || groupId.trim().length === 0 || !isSlugLikeId(groupId.trim())) {
64
+ throw makeValidationError('site-navigation-top-nav-group-id', 'Use a lowercase slug-like "groupId" for nav-group top navigation items.', { index, itemId: id.trim(), received: groupId });
65
+ }
66
+ return {
67
+ id: id.trim(),
68
+ type: 'nav-group',
69
+ groupId: groupId.trim(),
70
+ label,
71
+ };
72
+ }
73
+ const href = input.href;
74
+ if (typeof href !== 'string' || href.trim().length === 0) {
75
+ throw makeValidationError('site-navigation-top-nav-href', 'Provide a non-empty "href" for external top navigation items.', { index, itemId: id.trim(), received: href });
76
+ }
77
+ if (input.openInNewTab != null && typeof input.openInNewTab !== 'boolean') {
78
+ throw makeValidationError('site-navigation-top-nav-open-in-new-tab', 'Use a boolean for "openInNewTab" on external top navigation items.', { index, itemId: id.trim(), received: input.openInNewTab });
79
+ }
80
+ return {
81
+ id: id.trim(),
82
+ type: 'external',
83
+ href: href.trim(),
84
+ ...(typeof input.openInNewTab === 'boolean' ? { openInNewTab: input.openInNewTab } : {}),
85
+ label,
86
+ };
87
+ }
88
+ export function validateProjectConfig(input) {
89
+ if (!isRecord(input)) {
90
+ throw makeValidationError('config-must-be-object', 'Ensure anydocs.config.json contains a single JSON object.');
91
+ }
92
+ const version = input.version;
93
+ if (version !== 1) {
94
+ throw makeValidationError('version-must-be-1', 'Set "version" to 1 in anydocs.config.json.', { received: version });
95
+ }
96
+ const projectId = input.projectId;
97
+ if (typeof projectId !== 'string' || projectId.trim().length === 0) {
98
+ throw makeValidationError('project-id-required', 'Provide a non-empty "projectId" using URL-safe characters.', { received: projectId });
99
+ }
100
+ if (!/^[a-z0-9]+(?:-[a-z0-9]+)*$/.test(projectId)) {
101
+ throw makeValidationError('project-id-format', 'Use lowercase letters, numbers, and hyphens only for "projectId".', { received: projectId });
102
+ }
103
+ const name = input.name;
104
+ if (typeof name !== 'string' || name.trim().length === 0) {
105
+ throw makeValidationError('project-name-required', 'Provide a non-empty human-readable "name" in anydocs.config.json.', { received: name });
106
+ }
107
+ const defaultLanguage = input.defaultLanguage;
108
+ if (!isSupportedLanguage(defaultLanguage)) {
109
+ throw makeValidationError('default-language-invalid', `Set "defaultLanguage" to one of: ${SUPPORTED_DOCS_LANGUAGES.join(', ')}.`, { received: defaultLanguage });
110
+ }
111
+ const languages = input.languages;
112
+ if (!Array.isArray(languages) || languages.length === 0) {
113
+ throw makeValidationError('languages-required', 'Provide a non-empty "languages" array in anydocs.config.json.', { received: languages });
114
+ }
115
+ const uniqueLanguages = new Set();
116
+ for (const language of languages) {
117
+ if (!isSupportedLanguage(language)) {
118
+ throw makeValidationError('language-variant-invalid', `Only these languages are supported in Phase 1: ${SUPPORTED_DOCS_LANGUAGES.join(', ')}.`, { received: language });
119
+ }
120
+ uniqueLanguages.add(language);
121
+ }
122
+ if (!uniqueLanguages.has(defaultLanguage)) {
123
+ throw makeValidationError('default-language-must-be-enabled', 'Include the default language in the "languages" array.', { defaultLanguage, languages: [...uniqueLanguages] });
124
+ }
125
+ const site = input.site;
126
+ if (!isRecord(site)) {
127
+ throw makeValidationError('site-required', 'Provide a "site" object in anydocs.config.json.', { received: site });
128
+ }
129
+ const theme = site.theme;
130
+ if (!isRecord(theme)) {
131
+ throw makeValidationError('site-theme-required', 'Provide a "theme" object under "site" in anydocs.config.json.', { received: theme });
132
+ }
133
+ const themeId = theme.id;
134
+ if (typeof themeId !== 'string' || themeId.trim().length === 0) {
135
+ throw makeValidationError('site-theme-id-required', 'Provide a non-empty "site.theme.id" in anydocs.config.json.', { received: themeId });
136
+ }
137
+ if (!/^[a-z0-9]+(?:-[a-z0-9]+)*$/.test(themeId)) {
138
+ throw makeValidationError('site-theme-id-format', 'Use lowercase letters, numbers, and hyphens only for "site.theme.id".', { received: themeId });
139
+ }
140
+ const branding = theme.branding;
141
+ if (branding != null && !isRecord(branding)) {
142
+ throw makeValidationError('site-theme-branding-object', 'Use an object for "site.theme.branding" when specifying reader branding overrides.', { received: branding });
143
+ }
144
+ const siteTitle = branding?.siteTitle;
145
+ if (siteTitle != null && (typeof siteTitle !== 'string' || siteTitle.trim().length === 0)) {
146
+ throw makeValidationError('site-theme-branding-site-title-string', 'Use a non-empty string for "site.theme.branding.siteTitle" when overriding the reader title.', { received: siteTitle });
147
+ }
148
+ const homeLabel = branding?.homeLabel;
149
+ if (homeLabel != null && (typeof homeLabel !== 'string' || homeLabel.trim().length === 0)) {
150
+ throw makeValidationError('site-theme-branding-home-label-string', 'Use a non-empty string for "site.theme.branding.homeLabel" when overriding the footer home label.', { received: homeLabel });
151
+ }
152
+ const logoSrc = branding?.logoSrc;
153
+ if (logoSrc != null && (typeof logoSrc !== 'string' || logoSrc.trim().length === 0)) {
154
+ throw makeValidationError('site-theme-branding-logo-src-string', 'Use a non-empty string for "site.theme.branding.logoSrc" when configuring a sidebar logo URL or path.', { received: logoSrc });
155
+ }
156
+ const logoAlt = branding?.logoAlt;
157
+ if (logoAlt != null && (typeof logoAlt !== 'string' || logoAlt.trim().length === 0)) {
158
+ throw makeValidationError('site-theme-branding-logo-alt-string', 'Use a non-empty string for "site.theme.branding.logoAlt" when overriding sidebar logo alt text.', { received: logoAlt });
159
+ }
160
+ const chrome = theme.chrome;
161
+ if (chrome != null && !isRecord(chrome)) {
162
+ throw makeValidationError('site-theme-chrome-object', 'Use an object for "site.theme.chrome" when specifying reader chrome overrides.', { received: chrome });
163
+ }
164
+ const showSearch = chrome?.showSearch;
165
+ if (showSearch != null && typeof showSearch !== 'boolean') {
166
+ throw makeValidationError('site-theme-chrome-show-search-boolean', 'Use a boolean for "site.theme.chrome.showSearch" when toggling sidebar search visibility.', { received: showSearch });
167
+ }
168
+ const colors = theme.colors;
169
+ if (colors != null && !isRecord(colors)) {
170
+ throw makeValidationError('site-theme-colors-object', 'Use an object for "site.theme.colors" when specifying semantic theme color overrides.', { received: colors });
171
+ }
172
+ const colorEntries = [
173
+ ['primary', colors?.primary],
174
+ ['primaryForeground', colors?.primaryForeground],
175
+ ['accent', colors?.accent],
176
+ ['accentForeground', colors?.accentForeground],
177
+ ['sidebarActive', colors?.sidebarActive],
178
+ ['sidebarActiveForeground', colors?.sidebarActiveForeground],
179
+ ];
180
+ for (const [field, value] of colorEntries) {
181
+ if (value == null) {
182
+ continue;
183
+ }
184
+ if (typeof value !== 'string' || !isHexColor(value.trim())) {
185
+ throw makeValidationError(`site-theme-colors-${field}-hex`, `Use a "#RRGGBB" value for "site.theme.colors.${field}".`, { received: value });
186
+ }
187
+ }
188
+ const codeTheme = theme.codeTheme;
189
+ if (codeTheme != null && !SUPPORTED_DOCS_CODE_THEMES.includes(codeTheme)) {
190
+ throw makeValidationError('site-theme-code-theme-invalid', `Set "site.theme.codeTheme" to one of: ${SUPPORTED_DOCS_CODE_THEMES.join(', ')}.`, { received: codeTheme });
191
+ }
192
+ const navigation = site.navigation;
193
+ if (navigation != null && !isRecord(navigation)) {
194
+ throw makeValidationError('site-navigation-object', 'Use an object for "site.navigation" when specifying site-shell navigation settings.', { received: navigation });
195
+ }
196
+ const rawTopNav = navigation?.topNav;
197
+ if (rawTopNav != null && !Array.isArray(rawTopNav)) {
198
+ throw makeValidationError('site-navigation-top-nav-array', 'Use an array for "site.navigation.topNav" when specifying top navigation items.', { received: rawTopNav });
199
+ }
200
+ const topNav = rawTopNav?.map((item, index) => validateTopNavItem(item, index)) ?? [];
201
+ const topNavIds = new Set();
202
+ for (const item of topNav) {
203
+ if (topNavIds.has(item.id)) {
204
+ throw makeValidationError('site-navigation-top-nav-item-id-unique', 'Use unique ids for top navigation items.', { itemId: item.id });
205
+ }
206
+ topNavIds.add(item.id);
207
+ }
208
+ const build = input.build;
209
+ if (build != null && !isRecord(build)) {
210
+ throw makeValidationError('build-must-be-object', 'Use an object for "build" when specifying build options.', { received: build });
211
+ }
212
+ const outputDir = build?.outputDir;
213
+ if (outputDir != null && (typeof outputDir !== 'string' || outputDir.trim().length === 0)) {
214
+ throw makeValidationError('build-output-dir-string', 'Use a non-empty string for "build.outputDir" when overriding the output directory.', { received: outputDir });
215
+ }
216
+ return {
217
+ version: 1,
218
+ projectId,
219
+ name: name.trim(),
220
+ defaultLanguage,
221
+ languages: [...uniqueLanguages],
222
+ site: {
223
+ theme: {
224
+ id: themeId.trim(),
225
+ ...(branding
226
+ ? {
227
+ branding: {
228
+ ...(typeof siteTitle === 'string' ? { siteTitle: siteTitle.trim() } : {}),
229
+ ...(typeof homeLabel === 'string' ? { homeLabel: homeLabel.trim() } : {}),
230
+ ...(typeof logoSrc === 'string' ? { logoSrc: logoSrc.trim() } : {}),
231
+ ...(typeof logoAlt === 'string' ? { logoAlt: logoAlt.trim() } : {}),
232
+ },
233
+ }
234
+ : {}),
235
+ ...(chrome
236
+ ? {
237
+ chrome: {
238
+ ...(typeof showSearch === 'boolean' ? { showSearch } : {}),
239
+ },
240
+ }
241
+ : {}),
242
+ ...(colors
243
+ ? {
244
+ colors: {
245
+ ...(typeof colors.primary === 'string' ? { primary: colors.primary.trim() } : {}),
246
+ ...(typeof colors.primaryForeground === 'string'
247
+ ? { primaryForeground: colors.primaryForeground.trim() }
248
+ : {}),
249
+ ...(typeof colors.accent === 'string' ? { accent: colors.accent.trim() } : {}),
250
+ ...(typeof colors.accentForeground === 'string'
251
+ ? { accentForeground: colors.accentForeground.trim() }
252
+ : {}),
253
+ ...(typeof colors.sidebarActive === 'string'
254
+ ? { sidebarActive: colors.sidebarActive.trim() }
255
+ : {}),
256
+ ...(typeof colors.sidebarActiveForeground === 'string'
257
+ ? { sidebarActiveForeground: colors.sidebarActiveForeground.trim() }
258
+ : {}),
259
+ },
260
+ }
261
+ : {}),
262
+ ...(typeof codeTheme === 'string' ? { codeTheme: codeTheme } : {}),
263
+ },
264
+ ...(topNav.length > 0 ? { navigation: { topNav } } : {}),
265
+ },
266
+ ...(typeof outputDir === 'string' ? { build: { outputDir: outputDir.trim() } } : {}),
267
+ };
268
+ }
@@ -0,0 +1,137 @@
1
+ import type { DocsLang, NavItem, NavigationDoc, PageDoc, PageRender, PageReview, PageStatus } from '../types/docs.ts';
2
+ import type { ProjectConfig } from '../types/project.ts';
3
+ export type CreatePageInput<TContent = unknown> = {
4
+ projectRoot: string;
5
+ lang: DocsLang;
6
+ page: {
7
+ id: string;
8
+ slug: string;
9
+ title: string;
10
+ description?: string;
11
+ tags?: string[];
12
+ status?: PageStatus;
13
+ content?: TContent;
14
+ render?: PageRender;
15
+ review?: PageReview;
16
+ };
17
+ };
18
+ export type UpdatePagePatch<TContent = unknown> = {
19
+ slug?: string;
20
+ title?: string;
21
+ description?: string;
22
+ tags?: string[];
23
+ content?: TContent;
24
+ render?: PageRender;
25
+ review?: PageReview;
26
+ };
27
+ export type UpdatePageInput<TContent = unknown> = {
28
+ projectRoot: string;
29
+ lang: DocsLang;
30
+ pageId: string;
31
+ patch: UpdatePagePatch<TContent>;
32
+ regenerateRender?: boolean;
33
+ };
34
+ export type SetPageStatusInput = {
35
+ projectRoot: string;
36
+ lang: DocsLang;
37
+ pageId: string;
38
+ status: PageStatus;
39
+ };
40
+ export type DeletePageInput = {
41
+ projectRoot: string;
42
+ lang: DocsLang;
43
+ pageId: string;
44
+ };
45
+ export type BatchCreatePagesInput<TContent = unknown> = {
46
+ projectRoot: string;
47
+ lang: DocsLang;
48
+ pages: Array<CreatePageInput<TContent>['page']>;
49
+ };
50
+ export type BatchUpdatePagesInput<TContent = unknown> = {
51
+ projectRoot: string;
52
+ lang: DocsLang;
53
+ updates: Array<{
54
+ pageId: string;
55
+ patch: UpdatePagePatch<TContent>;
56
+ regenerateRender?: boolean;
57
+ }>;
58
+ };
59
+ export type BatchSetPageStatusesInput = {
60
+ projectRoot: string;
61
+ lang: DocsLang;
62
+ updates: Array<{
63
+ pageId: string;
64
+ status: PageStatus;
65
+ }>;
66
+ };
67
+ export type AuthoringPageResult<TContent = unknown> = {
68
+ filePath: string;
69
+ page: PageDoc<TContent>;
70
+ };
71
+ export type AuthoringDeletePageResult = {
72
+ filePath: string;
73
+ pageId: string;
74
+ lang: DocsLang;
75
+ removedNavigationRefs: number;
76
+ };
77
+ export type AuthoringBatchPagesResult<TContent = unknown> = {
78
+ count: number;
79
+ files: string[];
80
+ pages: Array<PageDoc<TContent>>;
81
+ };
82
+ export type AuthoringNavigationResult = {
83
+ filePath: string;
84
+ navigation: NavigationDoc;
85
+ };
86
+ export type SetNavigationInput = {
87
+ projectRoot: string;
88
+ lang: DocsLang;
89
+ navigation: NavigationDoc;
90
+ };
91
+ export type ReplaceNavigationItemsInput = {
92
+ projectRoot: string;
93
+ lang: DocsLang;
94
+ items: NavigationDoc['items'];
95
+ };
96
+ export type InsertNavigationItemInput = {
97
+ projectRoot: string;
98
+ lang: DocsLang;
99
+ item: NavItem;
100
+ parentPath?: string;
101
+ index?: number;
102
+ };
103
+ export type DeleteNavigationItemInput = {
104
+ projectRoot: string;
105
+ lang: DocsLang;
106
+ itemPath: string;
107
+ };
108
+ export type MoveNavigationItemInput = {
109
+ projectRoot: string;
110
+ lang: DocsLang;
111
+ itemPath: string;
112
+ parentPath?: string;
113
+ index?: number;
114
+ };
115
+ export type SetProjectLanguagesInput = {
116
+ projectRoot: string;
117
+ languages: DocsLang[];
118
+ defaultLanguage?: DocsLang;
119
+ };
120
+ export type AuthoringProjectConfigResult = {
121
+ filePath: string;
122
+ config: ProjectConfig;
123
+ };
124
+ export declare function createPage<TContent = unknown>(input: CreatePageInput<TContent>): Promise<AuthoringPageResult<TContent>>;
125
+ export declare function createPagesBatch<TContent = unknown>(input: BatchCreatePagesInput<TContent>): Promise<AuthoringBatchPagesResult<TContent>>;
126
+ export declare function updatePage<TContent = unknown>(input: UpdatePageInput<TContent>): Promise<AuthoringPageResult<TContent>>;
127
+ export declare function updatePagesBatch<TContent = unknown>(input: BatchUpdatePagesInput<TContent>): Promise<AuthoringBatchPagesResult<TContent>>;
128
+ export declare function setPageStatus<TContent = unknown>(input: SetPageStatusInput): Promise<AuthoringPageResult<TContent>>;
129
+ export declare function setPageStatusesBatch<TContent = unknown>(input: BatchSetPageStatusesInput): Promise<AuthoringBatchPagesResult<TContent>>;
130
+ export declare function deleteAuthoredPage(input: DeletePageInput): Promise<AuthoringDeletePageResult>;
131
+ export declare function setNavigation(input: SetNavigationInput): Promise<AuthoringNavigationResult>;
132
+ export declare function replaceNavigationItems(input: ReplaceNavigationItemsInput): Promise<AuthoringNavigationResult>;
133
+ export declare function insertNavigationItem(input: InsertNavigationItemInput): Promise<AuthoringNavigationResult>;
134
+ export declare function deleteNavigationItem(input: DeleteNavigationItemInput): Promise<AuthoringNavigationResult>;
135
+ export declare function moveNavigationItem(input: MoveNavigationItemInput): Promise<AuthoringNavigationResult>;
136
+ export declare function setProjectLanguages(input: SetProjectLanguagesInput): Promise<AuthoringProjectConfigResult>;
137
+ //# sourceMappingURL=authoring-service.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"authoring-service.d.ts","sourceRoot":"","sources":["../../src/services/authoring-service.ts"],"names":[],"mappings":"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"}