vagejs 0.0.0-stage → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (119) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +79 -2
  3. package/dist/audit/a11y.d.ts +13 -0
  4. package/dist/audit/a11y.js +33 -0
  5. package/dist/audit/audit.d.ts +31 -0
  6. package/dist/audit/audit.js +143 -0
  7. package/dist/audit/budgets.d.ts +22 -0
  8. package/dist/audit/budgets.js +106 -0
  9. package/dist/audit/lighthouse.d.ts +3 -0
  10. package/dist/audit/lighthouse.js +48 -0
  11. package/dist/audit/remote.d.ts +65 -0
  12. package/dist/audit/remote.js +123 -0
  13. package/dist/audit/vitals.d.ts +28 -0
  14. package/dist/audit/vitals.js +18 -0
  15. package/dist/checks/check.d.ts +29 -0
  16. package/dist/checks/check.js +330 -0
  17. package/dist/cli/create.d.ts +10 -0
  18. package/dist/cli/create.js +39 -0
  19. package/dist/cli/index.d.ts +2 -0
  20. package/dist/cli/index.js +604 -0
  21. package/dist/cli/info.d.ts +47 -0
  22. package/dist/cli/info.js +55 -0
  23. package/dist/content/markdown.d.ts +26 -0
  24. package/dist/content/markdown.js +51 -0
  25. package/dist/content/sanitize.d.ts +7 -0
  26. package/dist/content/sanitize.js +17 -0
  27. package/dist/core/build.d.ts +25 -0
  28. package/dist/core/build.js +54 -0
  29. package/dist/core/config.d.ts +171 -0
  30. package/dist/core/config.js +243 -0
  31. package/dist/core/errors.d.ts +5 -0
  32. package/dist/core/errors.js +9 -0
  33. package/dist/core/html.d.ts +2 -0
  34. package/dist/core/html.js +11 -0
  35. package/dist/core/loader.d.ts +10 -0
  36. package/dist/core/loader.js +16 -0
  37. package/dist/core/project-config.d.ts +3 -0
  38. package/dist/core/project-config.js +14 -0
  39. package/dist/core/render.d.ts +37 -0
  40. package/dist/core/render.js +62 -0
  41. package/dist/core/routes.d.ts +24 -0
  42. package/dist/core/routes.js +70 -0
  43. package/dist/core/site.d.ts +31 -0
  44. package/dist/core/site.js +159 -0
  45. package/dist/core/validate.d.ts +10 -0
  46. package/dist/core/validate.js +30 -0
  47. package/dist/deploy/cloudflare-pages.d.ts +20 -0
  48. package/dist/deploy/cloudflare-pages.js +40 -0
  49. package/dist/deploy/git.d.ts +20 -0
  50. package/dist/deploy/git.js +55 -0
  51. package/dist/deploy/github-pages.d.ts +33 -0
  52. package/dist/deploy/github-pages.js +99 -0
  53. package/dist/deploy/headers.d.ts +11 -0
  54. package/dist/deploy/headers.js +103 -0
  55. package/dist/deploy/publish.d.ts +45 -0
  56. package/dist/deploy/publish.js +148 -0
  57. package/dist/deploy/redirects.d.ts +7 -0
  58. package/dist/deploy/redirects.js +18 -0
  59. package/dist/deploy/secrets.d.ts +6 -0
  60. package/dist/deploy/secrets.js +66 -0
  61. package/dist/dev/guard.d.ts +9 -0
  62. package/dist/dev/guard.js +57 -0
  63. package/dist/dev/listen.d.ts +6 -0
  64. package/dist/dev/listen.js +13 -0
  65. package/dist/dev/preview.d.ts +6 -0
  66. package/dist/dev/preview.js +72 -0
  67. package/dist/dev/server.d.ts +8 -0
  68. package/dist/dev/server.js +102 -0
  69. package/dist/discovery/crawlers.d.ts +13 -0
  70. package/dist/discovery/crawlers.js +2 -0
  71. package/dist/discovery/llms.d.ts +12 -0
  72. package/dist/discovery/llms.js +19 -0
  73. package/dist/discovery/robots.d.ts +8 -0
  74. package/dist/discovery/robots.js +40 -0
  75. package/dist/discovery/sitemap.d.ts +8 -0
  76. package/dist/discovery/sitemap.js +11 -0
  77. package/dist/guidelines/monitor.d.ts +55 -0
  78. package/dist/guidelines/monitor.js +126 -0
  79. package/dist/guidelines/pack.d.ts +41 -0
  80. package/dist/guidelines/pack.js +13 -0
  81. package/dist/guidelines/rule-pack.json +611 -0
  82. package/dist/index.d.ts +11 -0
  83. package/dist/index.js +9 -0
  84. package/dist/integrations/api-keys.d.ts +26 -0
  85. package/dist/integrations/api-keys.js +65 -0
  86. package/dist/integrations/ga4-data.d.ts +13 -0
  87. package/dist/integrations/ga4-data.js +39 -0
  88. package/dist/integrations/google-auth.d.ts +47 -0
  89. package/dist/integrations/google-auth.js +157 -0
  90. package/dist/integrations/http.d.ts +15 -0
  91. package/dist/integrations/http.js +40 -0
  92. package/dist/integrations/indexnow.d.ts +18 -0
  93. package/dist/integrations/indexnow.js +38 -0
  94. package/dist/integrations/search-console.d.ts +25 -0
  95. package/dist/integrations/search-console.js +39 -0
  96. package/dist/integrations/tags.d.ts +22 -0
  97. package/dist/integrations/tags.js +67 -0
  98. package/dist/seo/head.d.ts +20 -0
  99. package/dist/seo/head.js +85 -0
  100. package/dist/seo/jsonld.d.ts +35 -0
  101. package/dist/seo/jsonld.js +31 -0
  102. package/dist/seo/urls.d.ts +3 -0
  103. package/dist/seo/urls.js +10 -0
  104. package/package.json +81 -4
  105. package/templates/starter/.env.example +12 -0
  106. package/templates/starter/.github/workflows/ci.yml +28 -0
  107. package/templates/starter/AGENTS.md +145 -0
  108. package/templates/starter/CLAUDE.md +3 -0
  109. package/templates/starter/_gitignore +8 -0
  110. package/templates/starter/package.json +16 -0
  111. package/templates/starter/public/apple-touch-icon.png +0 -0
  112. package/templates/starter/public/favicon.ico +0 -0
  113. package/templates/starter/public/favicon.svg +1 -0
  114. package/templates/starter/src/layouts/default.ts +37 -0
  115. package/templates/starter/src/pages/404.md +7 -0
  116. package/templates/starter/src/pages/about.md +8 -0
  117. package/templates/starter/src/pages/blog/first-post.md +10 -0
  118. package/templates/starter/src/pages/index.md +8 -0
  119. package/templates/starter/vage.config.ts +34 -0
@@ -0,0 +1,611 @@
1
+ {
2
+ "version": "2026.10.0",
3
+ "released": "2026-10-23",
4
+ "sources": [
5
+ {
6
+ "id": "google-search-essentials",
7
+ "provider": "Google",
8
+ "title": "Google Search Essentials",
9
+ "url": "https://developers.google.com/search/docs/essentials",
10
+ "category": "search",
11
+ "cadence": "weekly"
12
+ },
13
+ {
14
+ "id": "google-robots",
15
+ "provider": "Google",
16
+ "title": "Introduction to robots.txt",
17
+ "url": "https://developers.google.com/search/docs/crawling-indexing/robots/intro",
18
+ "category": "crawling",
19
+ "cadence": "weekly"
20
+ },
21
+ {
22
+ "id": "google-crawlers",
23
+ "provider": "Google",
24
+ "title": "Google's common crawlers (incl. Google-Extended)",
25
+ "url": "https://developers.google.com/crawling/docs/crawlers-fetchers/google-common-crawlers",
26
+ "category": "ai-crawlers",
27
+ "cadence": "daily"
28
+ },
29
+ {
30
+ "id": "google-sitemaps",
31
+ "provider": "Google",
32
+ "title": "Build and submit a sitemap",
33
+ "url": "https://developers.google.com/search/docs/crawling-indexing/sitemaps/build-sitemap",
34
+ "category": "crawling",
35
+ "cadence": "weekly"
36
+ },
37
+ {
38
+ "id": "sitemaps-protocol",
39
+ "provider": "sitemaps.org",
40
+ "title": "Sitemaps XML format",
41
+ "url": "https://www.sitemaps.org/protocol.html",
42
+ "category": "crawling",
43
+ "cadence": "weekly"
44
+ },
45
+ {
46
+ "id": "google-canonical",
47
+ "provider": "Google",
48
+ "title": "Consolidate duplicate URLs",
49
+ "url": "https://developers.google.com/search/docs/crawling-indexing/consolidate-duplicate-urls",
50
+ "category": "search",
51
+ "cadence": "weekly"
52
+ },
53
+ {
54
+ "id": "google-sd-policies",
55
+ "provider": "Google",
56
+ "title": "Structured data general guidelines",
57
+ "url": "https://developers.google.com/search/docs/appearance/structured-data/sd-policies",
58
+ "category": "structured-data",
59
+ "cadence": "weekly"
60
+ },
61
+ {
62
+ "id": "google-article",
63
+ "provider": "Google",
64
+ "title": "Article structured data",
65
+ "url": "https://developers.google.com/search/docs/appearance/structured-data/article",
66
+ "category": "structured-data",
67
+ "cadence": "weekly"
68
+ },
69
+ {
70
+ "id": "schema-org",
71
+ "provider": "Schema.org",
72
+ "title": "Schema.org documents",
73
+ "url": "https://schema.org/docs/documents.html",
74
+ "category": "structured-data",
75
+ "cadence": "weekly"
76
+ },
77
+ {
78
+ "id": "openai-bots",
79
+ "provider": "OpenAI",
80
+ "title": "Overview of OpenAI crawlers",
81
+ "url": "https://developers.openai.com/api/docs/bots",
82
+ "category": "ai-crawlers",
83
+ "cadence": "daily"
84
+ },
85
+ {
86
+ "id": "anthropic-crawlers",
87
+ "provider": "Anthropic",
88
+ "title": "Does Anthropic crawl data from the web?",
89
+ "url": "https://support.claude.com/en/articles/8896518-does-anthropic-crawl-data-from-the-web-and-how-can-site-owners-block-the-crawler",
90
+ "category": "ai-crawlers",
91
+ "cadence": "daily"
92
+ },
93
+ {
94
+ "id": "llms-txt",
95
+ "provider": "llmstxt.org",
96
+ "title": "The /llms.txt file (proposal)",
97
+ "url": "https://llmstxt.org/",
98
+ "category": "ai-discovery",
99
+ "cadence": "weekly"
100
+ },
101
+ {
102
+ "id": "web-vitals",
103
+ "provider": "Google (web.dev)",
104
+ "title": "Web Vitals",
105
+ "url": "https://web.dev/articles/vitals",
106
+ "category": "performance",
107
+ "cadence": "weekly"
108
+ },
109
+ {
110
+ "id": "psi-api",
111
+ "provider": "Google",
112
+ "title": "PageSpeed Insights API: get started",
113
+ "url": "https://developers.google.com/speed/docs/insights/v5/get-started",
114
+ "category": "performance",
115
+ "cadence": "weekly"
116
+ },
117
+ {
118
+ "id": "crux-api",
119
+ "provider": "Google (Chrome)",
120
+ "title": "CrUX API",
121
+ "url": "https://developer.chrome.com/docs/crux/api",
122
+ "category": "performance",
123
+ "cadence": "weekly"
124
+ },
125
+ {
126
+ "id": "w3c-wai",
127
+ "provider": "W3C",
128
+ "title": "W3C Accessibility Standards Overview",
129
+ "url": "https://www.w3.org/WAI/standards-guidelines/",
130
+ "category": "accessibility",
131
+ "cadence": "weekly"
132
+ },
133
+ {
134
+ "id": "google-consent",
135
+ "provider": "Google",
136
+ "title": "Set up consent mode on websites",
137
+ "url": "https://developers.google.com/tag-platform/security/guides/consent",
138
+ "category": "privacy",
139
+ "cadence": "weekly"
140
+ },
141
+ {
142
+ "id": "ga4-event-naming",
143
+ "provider": "Google",
144
+ "title": "[GA4] Event naming rules",
145
+ "url": "https://support.google.com/analytics/answer/13316687",
146
+ "category": "analytics",
147
+ "cadence": "weekly"
148
+ },
149
+ {
150
+ "id": "ga4-limits",
151
+ "provider": "Google",
152
+ "title": "[GA4] Event collection limits",
153
+ "url": "https://support.google.com/analytics/answer/9267744",
154
+ "category": "analytics",
155
+ "cadence": "weekly"
156
+ },
157
+ {
158
+ "id": "ga4-runreport",
159
+ "provider": "Google",
160
+ "title": "GA4 Data API: properties.runReport",
161
+ "url": "https://developers.google.com/analytics/devguides/reporting/data/v1/rest/v1beta/properties/runReport",
162
+ "category": "analytics",
163
+ "cadence": "weekly"
164
+ },
165
+ {
166
+ "id": "gsc-searchanalytics",
167
+ "provider": "Google",
168
+ "title": "Search Console API: searchanalytics.query",
169
+ "url": "https://developers.google.com/webmaster-tools/v1/searchanalytics/query",
170
+ "category": "search-console",
171
+ "cadence": "weekly"
172
+ },
173
+ {
174
+ "id": "google-oauth-native",
175
+ "provider": "Google",
176
+ "title": "OAuth 2.0 for iOS & desktop apps",
177
+ "url": "https://developers.google.com/identity/protocols/oauth2/native-app",
178
+ "category": "auth",
179
+ "cadence": "weekly"
180
+ },
181
+ {
182
+ "id": "gh-pages-workflows",
183
+ "provider": "GitHub",
184
+ "title": "Using custom workflows with GitHub Pages",
185
+ "url": "https://docs.github.com/en/pages/getting-started-with-github-pages/using-custom-workflows-with-github-pages",
186
+ "category": "hosting",
187
+ "cadence": "weekly"
188
+ },
189
+ {
190
+ "id": "gh-pages-custom-domain",
191
+ "provider": "GitHub",
192
+ "title": "Managing a custom domain for your GitHub Pages site",
193
+ "url": "https://docs.github.com/en/pages/configuring-a-custom-domain-for-your-github-pages-site/managing-a-custom-domain-for-your-github-pages-site",
194
+ "category": "hosting",
195
+ "cadence": "weekly"
196
+ },
197
+ {
198
+ "id": "bing-guidelines",
199
+ "provider": "Microsoft",
200
+ "title": "Bing Webmaster Guidelines",
201
+ "url": "https://www.bing.com/webmasters/help/webmaster-guidelines-30fba23a",
202
+ "category": "search",
203
+ "cadence": "weekly",
204
+ "monitor": "manual"
205
+ },
206
+ {
207
+ "id": "indexnow",
208
+ "provider": "IndexNow",
209
+ "title": "IndexNow documentation",
210
+ "url": "https://www.indexnow.org/documentation",
211
+ "category": "search",
212
+ "cadence": "weekly"
213
+ },
214
+ {
215
+ "id": "indexnow-faq",
216
+ "provider": "IndexNow",
217
+ "title": "IndexNow FAQ",
218
+ "url": "https://www.indexnow.org/faq",
219
+ "category": "search",
220
+ "cadence": "weekly"
221
+ },
222
+ {
223
+ "id": "clarity-consent",
224
+ "provider": "Microsoft",
225
+ "title": "Clarity Cookie Consent API - ConsentV2",
226
+ "url": "https://learn.microsoft.com/en-us/clarity/setup-and-installation/clarity-consent-api-v2",
227
+ "category": "privacy",
228
+ "cadence": "weekly"
229
+ },
230
+ {
231
+ "id": "plausible-events",
232
+ "provider": "Plausible",
233
+ "title": "Custom event goals",
234
+ "url": "https://plausible.io/docs/custom-event-goals",
235
+ "category": "analytics",
236
+ "cadence": "weekly"
237
+ },
238
+ {
239
+ "id": "cloudflare-redirects",
240
+ "provider": "Cloudflare",
241
+ "title": "Pages: redirects (_redirects)",
242
+ "url": "https://developers.cloudflare.com/pages/configuration/redirects/",
243
+ "category": "hosting",
244
+ "cadence": "weekly"
245
+ },
246
+ {
247
+ "id": "google-csp",
248
+ "provider": "Google",
249
+ "title": "Use a Content Security Policy with Google tags",
250
+ "url": "https://developers.google.com/tag-platform/security/guides/csp",
251
+ "category": "security",
252
+ "cadence": "weekly"
253
+ },
254
+ {
255
+ "id": "clarity-csp",
256
+ "provider": "Microsoft",
257
+ "title": "Clarity Content Security Policy",
258
+ "url": "https://learn.microsoft.com/en-us/clarity/setup-and-installation/clarity-csp",
259
+ "category": "security",
260
+ "cadence": "weekly"
261
+ },
262
+ {
263
+ "id": "cloudflare-headers",
264
+ "provider": "Cloudflare",
265
+ "title": "Pages: headers (_headers)",
266
+ "url": "https://developers.cloudflare.com/pages/configuration/headers/",
267
+ "category": "hosting",
268
+ "cadence": "weekly"
269
+ }
270
+ ],
271
+ "rules": [
272
+ {
273
+ "id": "robots.ai-crawlers",
274
+ "summary": "robots.txt tokens for AI crawlers, split into training vs search. Only documented robots.txt-honoring tokens; user-initiated fetchers excluded.",
275
+ "behaviorChanging": true,
276
+ "sources": [
277
+ "openai-bots",
278
+ "anthropic-crawlers",
279
+ "google-crawlers"
280
+ ],
281
+ "implementedIn": [
282
+ "src/discovery/crawlers.ts",
283
+ "src/discovery/robots.ts"
284
+ ],
285
+ "data": {
286
+ "crawlers": [
287
+ {
288
+ "token": "GPTBot",
289
+ "provider": "OpenAI",
290
+ "purpose": "training",
291
+ "source": "openai-bots"
292
+ },
293
+ {
294
+ "token": "OAI-SearchBot",
295
+ "provider": "OpenAI",
296
+ "purpose": "search",
297
+ "source": "openai-bots"
298
+ },
299
+ {
300
+ "token": "ClaudeBot",
301
+ "provider": "Anthropic",
302
+ "purpose": "training",
303
+ "source": "anthropic-crawlers"
304
+ },
305
+ {
306
+ "token": "Claude-SearchBot",
307
+ "provider": "Anthropic",
308
+ "purpose": "search",
309
+ "source": "anthropic-crawlers"
310
+ },
311
+ {
312
+ "token": "Google-Extended",
313
+ "provider": "Google",
314
+ "purpose": "training",
315
+ "source": "google-crawlers"
316
+ }
317
+ ]
318
+ }
319
+ },
320
+ {
321
+ "id": "sitemap.limits",
322
+ "summary": "Maximum URLs per sitemap file.",
323
+ "behaviorChanging": true,
324
+ "sources": [
325
+ "google-sitemaps",
326
+ "sitemaps-protocol"
327
+ ],
328
+ "implementedIn": [
329
+ "src/discovery/sitemap.ts"
330
+ ],
331
+ "data": {
332
+ "maxUrls": 50000
333
+ }
334
+ },
335
+ {
336
+ "id": "vitals.thresholds",
337
+ "summary": "Core Web Vitals good / poor thresholds at the 75th percentile.",
338
+ "behaviorChanging": true,
339
+ "sources": [
340
+ "web-vitals"
341
+ ],
342
+ "implementedIn": [
343
+ "src/audit/vitals.ts"
344
+ ],
345
+ "data": {
346
+ "lcp": {
347
+ "good": 2500,
348
+ "poor": 4000
349
+ },
350
+ "inp": {
351
+ "good": 200,
352
+ "poor": 500
353
+ },
354
+ "cls": {
355
+ "good": 0.1,
356
+ "poor": 0.25
357
+ }
358
+ }
359
+ },
360
+ {
361
+ "id": "ga4.naming",
362
+ "summary": "GA4 event and parameter naming rules and length limits.",
363
+ "behaviorChanging": true,
364
+ "sources": [
365
+ "ga4-event-naming",
366
+ "ga4-limits"
367
+ ],
368
+ "implementedIn": [
369
+ "src/core/config.ts"
370
+ ],
371
+ "data": {
372
+ "maxNameLength": 40,
373
+ "reservedParamPrefixes": [
374
+ "_",
375
+ "firebase_",
376
+ "ga_",
377
+ "google_",
378
+ "gtag."
379
+ ]
380
+ }
381
+ },
382
+ {
383
+ "id": "consent.default-order",
384
+ "summary": "Consent defaults are set before any measurement command; four consent types.",
385
+ "behaviorChanging": true,
386
+ "sources": [
387
+ "google-consent"
388
+ ],
389
+ "implementedIn": [
390
+ "src/integrations/tags.ts"
391
+ ],
392
+ "data": {
393
+ "types": [
394
+ "ad_storage",
395
+ "ad_user_data",
396
+ "ad_personalization",
397
+ "analytics_storage"
398
+ ]
399
+ }
400
+ },
401
+ {
402
+ "id": "seo.canonical-and-structured-data",
403
+ "summary": "Absolute canonical URLs; structured data must match visible content; Article recommended properties.",
404
+ "behaviorChanging": false,
405
+ "sources": [
406
+ "google-canonical",
407
+ "google-sd-policies",
408
+ "google-article",
409
+ "schema-org"
410
+ ],
411
+ "implementedIn": [
412
+ "src/seo/head.ts",
413
+ "src/checks/check.ts"
414
+ ]
415
+ },
416
+ {
417
+ "id": "llms-txt.format",
418
+ "summary": "llms.txt layout (H1 title, blockquote summary, link sections). An emerging convention.",
419
+ "behaviorChanging": false,
420
+ "sources": [
421
+ "llms-txt"
422
+ ],
423
+ "implementedIn": [
424
+ "src/discovery/llms.ts"
425
+ ]
426
+ },
427
+ {
428
+ "id": "audit.field-data-source",
429
+ "summary": "Field data from the CrUX API (PSI field data is planned for discontinuation); lab data from PageSpeed Insights.",
430
+ "behaviorChanging": false,
431
+ "sources": [
432
+ "psi-api",
433
+ "crux-api"
434
+ ],
435
+ "implementedIn": [
436
+ "src/audit/remote.ts"
437
+ ]
438
+ },
439
+ {
440
+ "id": "accessibility.baseline",
441
+ "summary": "Automated accessibility rules (axe-core) as a baseline, not WCAG conformance.",
442
+ "behaviorChanging": false,
443
+ "sources": [
444
+ "w3c-wai"
445
+ ],
446
+ "implementedIn": [
447
+ "src/audit/a11y.ts",
448
+ "src/checks/check.ts"
449
+ ]
450
+ },
451
+ {
452
+ "id": "google-apis.reporting",
453
+ "summary": "Desktop OAuth (loopback + PKCE) with read-only scopes; Search Analytics and GA4 runReport request shapes.",
454
+ "behaviorChanging": false,
455
+ "sources": [
456
+ "google-oauth-native",
457
+ "gsc-searchanalytics",
458
+ "ga4-runreport"
459
+ ],
460
+ "implementedIn": [
461
+ "src/integrations/google-auth.ts",
462
+ "src/integrations/search-console.ts",
463
+ "src/integrations/ga4-data.ts"
464
+ ]
465
+ },
466
+ {
467
+ "id": "hosting.github-pages",
468
+ "summary": "GitHub Pages via Actions: permissions, environment, artifact; CNAME not required.",
469
+ "behaviorChanging": true,
470
+ "sources": [
471
+ "gh-pages-workflows",
472
+ "gh-pages-custom-domain"
473
+ ],
474
+ "implementedIn": [
475
+ "src/deploy/github-pages.ts"
476
+ ]
477
+ },
478
+ {
479
+ "id": "search.general",
480
+ "summary": "General search guidance tracked for future rules.",
481
+ "behaviorChanging": false,
482
+ "sources": [
483
+ "google-search-essentials",
484
+ "google-robots",
485
+ "bing-guidelines"
486
+ ],
487
+ "implementedIn": []
488
+ },
489
+ {
490
+ "id": "indexnow.protocol",
491
+ "summary": "IndexNow submission: shared endpoint, up to 10,000 URLs per request, key 8-128 chars served at /<key>.txt; 200/202 accepted.",
492
+ "behaviorChanging": true,
493
+ "sources": [
494
+ "indexnow",
495
+ "indexnow-faq"
496
+ ],
497
+ "implementedIn": [
498
+ "src/integrations/indexnow.ts"
499
+ ],
500
+ "data": {
501
+ "endpoint": "https://api.indexnow.org/indexnow",
502
+ "maxUrls": 10000,
503
+ "keyPattern": "^[A-Za-z0-9-]{8,128}$"
504
+ }
505
+ },
506
+ {
507
+ "id": "clarity.consent",
508
+ "summary": "Clarity consent via consentv2 with ad_Storage / analytics_Storage.",
509
+ "behaviorChanging": true,
510
+ "sources": [
511
+ "clarity-consent"
512
+ ],
513
+ "implementedIn": [
514
+ "src/integrations/tags.ts"
515
+ ]
516
+ },
517
+ {
518
+ "id": "plausible.events",
519
+ "summary": "Plausible custom events: plausible(name, { props }).",
520
+ "behaviorChanging": false,
521
+ "sources": [
522
+ "plausible-events"
523
+ ],
524
+ "implementedIn": [
525
+ "src/integrations/tags.ts"
526
+ ]
527
+ },
528
+ {
529
+ "id": "cloudflare.redirects",
530
+ "summary": "_redirects format 'source destination status', up to 2,000 static rules.",
531
+ "behaviorChanging": true,
532
+ "sources": [
533
+ "cloudflare-redirects"
534
+ ],
535
+ "implementedIn": [
536
+ "src/deploy/cloudflare-pages.ts"
537
+ ],
538
+ "data": {
539
+ "maxStaticRules": 2000
540
+ }
541
+ },
542
+ {
543
+ "id": "csp.providers",
544
+ "summary": "CSP sources required by analytics providers (GA4 without Ads features, Tag Manager, Clarity).",
545
+ "behaviorChanging": true,
546
+ "sources": [
547
+ "google-csp",
548
+ "clarity-csp"
549
+ ],
550
+ "implementedIn": [
551
+ "src/deploy/headers.ts"
552
+ ],
553
+ "data": {
554
+ "google": {
555
+ "script-src": [
556
+ "https://www.googletagmanager.com"
557
+ ],
558
+ "connect-src": [
559
+ "https://www.googletagmanager.com",
560
+ "https://*.google-analytics.com",
561
+ "https://*.google.com"
562
+ ],
563
+ "img-src": [
564
+ "https://www.googletagmanager.com",
565
+ "https://*.google-analytics.com"
566
+ ],
567
+ "frame-src": [
568
+ "https://www.googletagmanager.com"
569
+ ]
570
+ },
571
+ "clarity": {
572
+ "script-src": [
573
+ "https://*.clarity.ms",
574
+ "https://c.bing.com"
575
+ ],
576
+ "connect-src": [
577
+ "https://*.clarity.ms",
578
+ "https://c.bing.com"
579
+ ],
580
+ "img-src": [
581
+ "https://*.clarity.ms",
582
+ "https://c.bing.com"
583
+ ]
584
+ }
585
+ }
586
+ },
587
+ {
588
+ "id": "cloudflare.headers",
589
+ "summary": "_headers format; up to 100 rules, 2,000 characters per line.",
590
+ "behaviorChanging": true,
591
+ "sources": [
592
+ "cloudflare-headers"
593
+ ],
594
+ "implementedIn": [
595
+ "src/deploy/headers.ts"
596
+ ],
597
+ "data": {
598
+ "maxLineLength": 2000
599
+ }
600
+ }
601
+ ],
602
+ "changelog": [
603
+ {
604
+ "version": "2026.10.0",
605
+ "date": "2026-10-23",
606
+ "summary": "Initial rule pack (unreleased; extended during Phase 8 and the security review with IndexNow, Clarity, Plausible, Cloudflare Pages and CSP provider rules). Facts checked against the cited sources on 2026-10-23 during implementation.",
607
+ "reviewedBy": "A G E Venkatesh",
608
+ "contentHash": "8c7272511f733c01984ce1d962b39e2d521a88b31a5c958a95307a04b82bb3dd"
609
+ }
610
+ ]
611
+ }
@@ -0,0 +1,11 @@
1
+ export { defineConfig, type SiteConfig, type UserConfig } from "./core/config.js";
2
+ export { escapeHtml } from "./core/html.js";
3
+ export type { Layout, LayoutProps } from "./core/render.js";
4
+ export type { Frontmatter } from "./content/markdown.js";
5
+ export { build, type BuildResult } from "./core/build.js";
6
+ export { startDevServer } from "./dev/server.js";
7
+ export { startPreviewServer } from "./dev/preview.js";
8
+ export { VageError } from "./core/errors.js";
9
+ export { check, type CheckResult, type Finding } from "./checks/check.js";
10
+ export { article, breadcrumbList, jsonLdScript, organization, website, type Thing } from "./seo/jsonld.js";
11
+ export { AI_CRAWLERS, type CrawlerToken } from "./discovery/crawlers.js";
package/dist/index.js ADDED
@@ -0,0 +1,9 @@
1
+ export { defineConfig } from "./core/config.js";
2
+ export { escapeHtml } from "./core/html.js";
3
+ export { build } from "./core/build.js";
4
+ export { startDevServer } from "./dev/server.js";
5
+ export { startPreviewServer } from "./dev/preview.js";
6
+ export { VageError } from "./core/errors.js";
7
+ export { check } from "./checks/check.js";
8
+ export { article, breadcrumbList, jsonLdScript, organization, website } from "./seo/jsonld.js";
9
+ export { AI_CRAWLERS } from "./discovery/crawlers.js";
@@ -0,0 +1,26 @@
1
+ /**
2
+ * The user's own Google Cloud API keys for audits. VAGE JS never ships or
3
+ * shares keys: each user brings theirs (env var, or saved with `vage connect`).
4
+ * Saved keys live next to the Google token, outside any project, mode 0600.
5
+ */
6
+ export declare const API_KEYS: {
7
+ readonly pagespeed: {
8
+ readonly env: "PAGESPEED_API_KEY";
9
+ readonly label: "PageSpeed Insights API";
10
+ readonly howTo: "Google Cloud Console → APIs & Services → enable “PageSpeed Insights API” → Credentials → Create credentials → API key (restrict it to that API).";
11
+ };
12
+ readonly crux: {
13
+ readonly env: "CRUX_API_KEY";
14
+ readonly label: "Chrome UX Report (CrUX) API";
15
+ readonly howTo: "Google Cloud Console → APIs & Services → enable “Chrome UX Report API” → Credentials → Create credentials → API key (one key can serve both APIs).";
16
+ };
17
+ };
18
+ export type ApiKeyName = keyof typeof API_KEYS;
19
+ type Env = Record<string, string | undefined>;
20
+ export declare function apiKeysPath(env?: Env): string;
21
+ /** Environment variable first, then the key saved with `vage connect`. */
22
+ export declare function resolveApiKey(name: ApiKeyName, env?: Env): string | undefined;
23
+ export declare function saveApiKey(name: ApiKeyName, value: string, env?: Env): string;
24
+ export declare function removeApiKey(name: ApiKeyName, env?: Env): boolean;
25
+ export declare function missingKeyMessage(name: ApiKeyName): string;
26
+ export {};