@grove-dev/core 0.2.2 → 0.2.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/validate.js CHANGED
@@ -1,7 +1,8 @@
1
1
  import { access, readdir, readFile } from "node:fs/promises";
2
2
  import { basename, join, resolve } from "node:path";
3
3
  import { parse as parseYaml } from "yaml";
4
- import { blueprintKind, decisionsFileSchema, healthFileSchema, recordsFileSchema, unwrapDecisions, unwrapHealth, unwrapRecords, } from "./schema.js";
4
+ import { ZodError } from "zod";
5
+ import { blueprintKind, decisionsFileSchema, healthFileSchema, recordsFileSchema, unwrapDecisions, unwrapHealth, } from "./schema.js";
5
6
  import { readYamlFile } from "./io.js";
6
7
  async function exists(path) {
7
8
  try {
@@ -14,9 +15,13 @@ async function exists(path) {
14
15
  }
15
16
  /**
16
17
  * Validate a Grove project: read every record YAML under
17
- * `config.paths.recordsDir`, check for duplicate slugs, missing
18
- * required fields, taxonomy reference problems, and dangling health
19
- * or decision references.
18
+ * `config.paths.recordsDir`, run full Zod parsing, and surface any
19
+ * schema, slug, link, health, or decision reference issues.
20
+ *
21
+ * Each record is run through the same Zod schema the build pipeline
22
+ * uses (see `recordsFileSchema`). Validation catches both schema
23
+ * problems (missing fields, wrong types) and reference problems
24
+ * (duplicate slugs, missing health entries, dangling decision ids).
20
25
  */
21
26
  export async function validateProject(config, opts = {}) {
22
27
  const errors = [];
@@ -33,13 +38,25 @@ export async function validateProject(config, opts = {}) {
33
38
  const expectedKind = blueprintKind[config.blueprint];
34
39
  const entries = await readdir(recordsDir).catch(() => []);
35
40
  const files = entries.filter((f) => f.endsWith(".yml")).sort();
36
- const records = [];
37
41
  const slugs = new Set();
42
+ /** Slugs that have a github link and therefore need a health entry. */
43
+ const slugsNeedingHealth = new Set();
38
44
  for (const file of files) {
39
45
  const fileSlug = basename(file, ".yml");
40
46
  const text = await readFile(join(recordsDir, file), "utf8");
41
47
  const raw = parseYaml(text);
42
- const obj = (raw ?? {});
48
+ if (raw === null || typeof raw !== "object" || Array.isArray(raw)) {
49
+ errors.push({
50
+ code: "schema_error",
51
+ message: `${fileSlug}: record file is empty or not a YAML mapping`,
52
+ severity: "error",
53
+ });
54
+ slugs.add(fileSlug);
55
+ continue;
56
+ }
57
+ const obj = raw;
58
+ // Slug uniqueness — even if a record later fails Zod parse, we
59
+ // still need to flag a duplicate filename as an error.
43
60
  if (slugs.has(fileSlug)) {
44
61
  errors.push({
45
62
  code: "duplicate_slug",
@@ -48,62 +65,101 @@ export async function validateProject(config, opts = {}) {
48
65
  });
49
66
  }
50
67
  slugs.add(fileSlug);
51
- if (!obj.description || !obj.description.trim()) {
52
- errors.push({
53
- code: "missing_description",
54
- message: `${fileSlug} is missing a description`,
55
- severity: "error",
68
+ // Full Zod parse — this is the source of truth for "is this a
69
+ // valid record". Each issue becomes a `zod_error` validation
70
+ // issue with the issue path baked into the message. If the
71
+ // parse throws something that isn't a ZodError (e.g. file
72
+ // doesn't exist anymore), surface it as a generic schema error.
73
+ if (!obj.kind)
74
+ obj.kind = expectedKind;
75
+ let parsed;
76
+ try {
77
+ parsed = recordsFileSchema.parse(obj);
78
+ }
79
+ catch (err) {
80
+ if (err instanceof ZodError) {
81
+ for (const issue of err.issues) {
82
+ const where = issue.path.length > 0 ? issue.path.join(".") : "(root)";
83
+ errors.push({
84
+ code: "zod_error",
85
+ message: `${fileSlug}: ${where} ${issue.message}`,
86
+ severity: "error",
87
+ });
88
+ }
89
+ }
90
+ else {
91
+ errors.push({
92
+ code: "schema_error",
93
+ message: `${fileSlug}: ${err.message}`,
94
+ severity: "error",
95
+ });
96
+ }
97
+ continue;
98
+ }
99
+ // Override the filename-derived slug with the record's own slug
100
+ // before downstream checks (links/health) consume it. Filename
101
+ // and record.slug must agree; mismatch is itself a warning.
102
+ if (parsed.slug !== fileSlug) {
103
+ warnings.push({
104
+ code: "slug_mismatch",
105
+ message: `${fileSlug}: record slug "${parsed.slug}" does not match filename`,
106
+ severity: "warning",
56
107
  });
57
108
  }
58
- const kind = obj.kind ?? expectedKind;
59
- if (kind !== expectedKind) {
109
+ // Records that link to a GitHub repo need a matching health entry
110
+ // so list/detail UIs can render staleness signals. Track here and
111
+ // cross-check against health.yml below.
112
+ const repoUrl = parsed.repoUrl;
113
+ const linksGithub = parsed.links?.github;
114
+ if (repoUrl || linksGithub) {
115
+ slugsNeedingHealth.add(fileSlug);
116
+ }
117
+ }
118
+ if (await exists(resolve(process.cwd(), config.paths.health))) {
119
+ let health = [];
120
+ try {
121
+ health = unwrapHealth(healthFileSchema.parse(await readYamlFile(config.paths.health)));
122
+ }
123
+ catch (err) {
60
124
  errors.push({
61
- code: "kind_blueprint_mismatch",
62
- message: `${fileSlug}: kind "${kind}" does not match blueprint "${config.blueprint}" (expected "${expectedKind}")`,
125
+ code: "health_file_invalid",
126
+ message: `${config.paths.health}: ${err.message}`,
63
127
  severity: "error",
64
128
  });
65
129
  }
66
- const links = obj.links ?? {};
67
- // Blueprint-aware link check: each blueprint has a different
68
- // canonical "where does this record live" answer.
69
- // project-directory → github OR website
70
- // resource-hub → source OR github OR website
71
- // ecosystem-map → website
72
- const linkOk = config.blueprint === "project-directory"
73
- ? Boolean(links.github || links.website)
74
- : config.blueprint === "resource-hub"
75
- ? Boolean(links.source || links.github || links.website)
76
- : Boolean(links.website);
77
- if (!linkOk) {
78
- const required = config.blueprint === "project-directory"
79
- ? "github or website"
80
- : config.blueprint === "resource-hub"
81
- ? "source, github, or website"
82
- : "website";
130
+ const healthIds = new Set(health.map((entry) => entry.id));
131
+ for (const slug of slugsNeedingHealth) {
132
+ if (healthIds.has(slug))
133
+ continue;
83
134
  errors.push({
84
- code: "missing_link",
85
- message: `${fileSlug} has no ${required} link`,
135
+ code: "missing_health",
136
+ message: `${slug} has a GitHub link but no health entry`,
86
137
  severity: "error",
87
138
  });
88
139
  }
89
- records.push(obj);
90
140
  }
91
- if (await exists(resolve(process.cwd(), config.paths.health))) {
92
- const health = unwrapHealth(healthFileSchema.parse(await readYamlFile(config.paths.health)));
93
- const healthIds = new Set(health.map((entry) => entry.id));
94
- for (const record of records) {
95
- const links = record.links;
96
- if (links?.github && !healthIds.has(record.slug)) {
97
- errors.push({
98
- code: "missing_health",
99
- message: `${record.slug} has a GitHub link but no health entry`,
100
- severity: "error",
101
- });
102
- }
103
- }
141
+ else if (slugsNeedingHealth.size > 0) {
142
+ // Health file is optional, but if any record points at a GitHub
143
+ // repo we expect a health file to exist (or `sync github` to
144
+ // produce one). Flag it as a warning so the operator knows.
145
+ warnings.push({
146
+ code: "missing_health_file",
147
+ message: `${config.paths.health} is missing but ${slugsNeedingHealth.size} record(s) link to GitHub repos`,
148
+ severity: "warning",
149
+ });
104
150
  }
105
151
  if (await exists(resolve(process.cwd(), config.paths.decisions))) {
106
- const decisions = unwrapDecisions(decisionsFileSchema.parse(await readYamlFile(config.paths.decisions)));
152
+ let decisions = [];
153
+ try {
154
+ decisions = unwrapDecisions(decisionsFileSchema.parse(await readYamlFile(config.paths.decisions)));
155
+ }
156
+ catch (err) {
157
+ errors.push({
158
+ code: "decisions_file_invalid",
159
+ message: `${config.paths.decisions}: ${err.message}`,
160
+ severity: "error",
161
+ });
162
+ }
107
163
  for (const decision of decisions) {
108
164
  if (!slugs.has(decision.id)) {
109
165
  errors.push({
@@ -128,11 +184,22 @@ function finalize(errors, warnings, strict = false) {
128
184
  }
129
185
  /**
130
186
  * Load and normalize every record YAML under `config.paths.recordsDir`.
131
- * Records that fail validation are skipped silently — use
132
- * `validateProject` to surface the failures.
187
+ *
188
+ * @param config Grove config (provides `paths.recordsDir` and `blueprint`)
189
+ * @param opts.onError 'skip' (default) silently drops schema failures;
190
+ * 'throw' raises on the first failure with the file slug and the
191
+ * Zod issue path in the error message.
192
+ * @param opts.cwd Working directory to resolve `paths.recordsDir`
193
+ * against. Defaults to `process.cwd()`.
194
+ *
195
+ * For callers that want the strict-by-default behaviour, see
196
+ * `loadRecordsOrThrow`. `validateProject` is the recommended
197
+ * surface for surfacing failures with full error reporting.
133
198
  */
134
- export async function loadRecords(config) {
135
- const recordsDir = resolve(process.cwd(), config.paths.recordsDir);
199
+ export async function loadRecords(config, opts = {}) {
200
+ const onError = opts.onError ?? "skip";
201
+ const cwd = opts.cwd ?? process.cwd();
202
+ const recordsDir = resolve(cwd, config.paths.recordsDir);
136
203
  const entries = await readdir(recordsDir).catch(() => []);
137
204
  const files = entries.filter((f) => f.endsWith(".yml")).sort();
138
205
  const expectedKind = blueprintKind[config.blueprint];
@@ -141,17 +208,34 @@ export async function loadRecords(config) {
141
208
  const fileSlug = basename(file, ".yml");
142
209
  const text = await readFile(join(recordsDir, file), "utf8");
143
210
  const raw = parseYaml(text);
144
- if (!raw || typeof raw !== "object")
211
+ if (!raw || typeof raw !== "object") {
212
+ if (onError === "throw") {
213
+ throw new Error(`${fileSlug}: record file is empty or not a YAML mapping`);
214
+ }
145
215
  continue;
216
+ }
146
217
  if (!raw.kind)
147
218
  raw.kind = expectedKind;
148
219
  try {
149
- out.push(unwrapRecords(recordsFileSchema.parse([raw]))[0]);
220
+ const parsed = recordsFileSchema.parse(raw);
221
+ parsed.slug = fileSlug;
222
+ out.push(parsed);
150
223
  }
151
- catch {
224
+ catch (err) {
225
+ if (onError === "throw")
226
+ throw err;
152
227
  // skip — validation should have caught this
153
228
  }
154
229
  }
155
230
  return out;
156
231
  }
232
+ /**
233
+ * Strict variant of `loadRecords` — throws on the first schema failure
234
+ * with the file slug and the Zod issue path in the error message.
235
+ * Recommended for build pipelines; `loadRecords` is the lenient
236
+ * helper for previews and dev-time inspection.
237
+ */
238
+ export function loadRecordsOrThrow(config, opts = {}) {
239
+ return loadRecords(config, { ...opts, onError: "throw" });
240
+ }
157
241
  //# sourceMappingURL=validate.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"validate.js","sourceRoot":"","sources":["../src/validate.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"validate.js","sourceRoot":"","sources":["../src/validate.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@grove-dev/core",
3
- "version": "0.2.2",
3
+ "version": "0.2.5",
4
4
  "type": "module",
5
5
  "description": "Headless engine for Grove: resource schema, config, importers, validators, taxonomy, sitemap, llms.txt, and the data build pipeline.",
6
6
  "license": "MIT",