Registro público
Informe de salud del softwareesquema 0.27.0 · métricas 1.13.0 · 2026-07-23 21:57 UTC

Open-Tech-Foundation / Web-App-Framework

A high-performance, zero-VDOM framework that compiles JSX to native DOM using signals and standard Web Components.

JavaScript · Rust · MDXMIT★ 0 estrellas⑂ 0 forksdesde abr 2026Ver en GitHub ↗

Open-Tech-Foundation/Web-App-Framework tiene un índice de salud de 57 sobre 100, lo que lo sitúa en la banda Moderado. Su puntuación más alta es Vitality (82/100) y la más baja, Security (30/100). Se actualizó por última vez hace 4 días. Una sola persona concentra la mayor parte del trabajo reciente.

57
global / 100
Moderado

Índice de salud del software

Las métricas se agrupan en categorías ponderadas sobre una escala de 1 a 100. El resultado global parte de su media; cuando la evidencia pública activa la Política de Jurisdicciones de Alto Riesgo, la calificación se ajusta y recibe el límite 49 (En riesgo). Preparación para IA queda fuera.

57
Excelente85-100Ejemplar; cumple prácticamente todos los criterios evaluados
Bueno70-84Saludable; carencias menores
Moderado50-69Aceptable con carencias notables; se recomienda revisión
En riesgo30-49Debilidades significativas; su adopción exige cautela
Crítico1-29Problemas graves (proyecto abandonado, un solo mantenedor, sin higiene)
VitalidadComunidad yAdopciónSostenibilidady GobernanzaCalidad deIngenieríaSeguridadPreparaciónpara IA

Perfil de puntuación

Cada eje es una categoría. La forma importa más que la media: un proyecto sano llena toda la figura, mientras que un perfil de picos y cráteres indica que la fortaleza en una dimensión enmascara el riesgo en otra.

Titularidad

2 seguidores41 repositorios públicosdesde abr 2019

Este repositorio está respaldado por una organización: una custodia compartida y responsable que puede sobrevivir a cualquier mantenedor individual.

Ecosistemas de paquetes

RegistroPaqueteVersiónDescargas / mesVersionesÚltima publicaciónEtiquetas
npm@opentf/web0.20.0360720hace 5 díasopentfweb-componentssignalsreactivityruntimessg
npm@opentf/web-cli1.18.0349522hace 4 díasopentfwebdev-serverssgrolldowntoolchain
npm@opentf/web-docs0.17.0301517hace 5 díasopentfdocumentationdocsmdxstatic-site-generatorssg
npm@opentf/web-form1.15.0258118hace 5 días
npm@opentf/web-i18n1.15.0256315hace 5 díasopentfi18ninternationalizationicuintllocalization
npm@opentf/web-test1.15.0248116hace 5 días

Métricas por categoría

Vitalidad

¿Está vivo el proyecto: se escribe código y se publican versiones?

82Bueno · 22% del índice global
Cómo se puntúa
36/36Recencia de push — último push hace 4 días
6.2/36Cadencia de commits — 9/52 semanas con commits
18/18Volumen de commits — 596 commits en el último año
10/10OpenSSF Scorecard: Maintained — 30 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10
Datos de entrada utilizados
commits_last_year596
human_commit_share1
days_since_last_push4
active_weeks_last_year9
Cómo se puntúa
27/27Publica versiones — 100 versiones publicadas
36/36Recencia de las versiones — última versión hace 4 días
27/27Cadencia de publicación — una versión cada ~0,1 días
0/10OpenSSF Scorecard: Signed-Releases — sin datos
Datos de entrada utilizados
releases_count100
latest_release_tag@opentf/web-cli@1.18.0
releases_from_tagsno
days_since_latest_release4
mean_days_between_releases0,1
Excluidos de la puntuación (sin datos o no aplicable): OpenSSF Scorecard: Signed-Releases. Los pesos restantes se han renormalizado.

Comunidad y Adopción

¿Tiene el proyecto usuarios, descargas, atención y unas condiciones acogedoras para quienes contribuyen?

36En riesgo · 18% del índice global
Cómo se puntúa
0/60Estrellas — 0 estrellas
0/25Forks — 0 forks
0/15Observadores — 0 observadores
Datos de entrada utilizados
forks0
stars0
watchers0
growth_stateunverified
growth_factor_pct100
growth_unverified_reasonno_history
Cómo se puntúa
22.5/22.5README
22.5/22.5Licencia — licencia reconocida (MIT)
0/18Guía CONTRIBUTING
0/13.5Código de conducta
0/7.2Plantilla de issues
0/6.3Plantilla de PR
Datos de entrada utilizados
has_readme
has_license
has_contributingno
has_issue_templateno
has_code_of_conductno
has_pull_request_templateno
Cómo se puntúa
56.7/80Descargas mensuales — 17.742 descargas/mes en npm
0/20Dependientes en el registro — no lo informa este ecosistema
Datos de entrada utilizados
packages@opentf/web, @opentf/web-cli, @opentf/web-docs, @opentf/web-form, @opentf/web-i18n, @opentf/web-test
dependents
ecosystemsnpm
total_downloads
monthly_downloads17.742
Excluidos de la puntuación (sin datos o no aplicable): Dependientes en el registro. Los pesos restantes se han renormalizado.

Sostenibilidad y Gobernanza

¿Sobrevivirá el proyecto a sus personas: factor bus, capacidad de respuesta, quién lo respalda y mantenimiento del paquete?

55Moderado · 24% del índice global
Cómo se puntúa
9/54Factor bus — la mitad de los commits recae en 1 contribuyente(s)
0/22.5Distribución de commits — el principal contribuyente firma el 100% de los commits
1.4/13.5Amplitud de contribuyentes — 1 contribuyentes
0/10OpenSSF Scorecard: Contributors — project has 0 contributing companies or organizations -- score normalized to 0
Datos de entrada utilizados
bus_factor1
contributors_sampled1
top_contributor_share1
Cómo se puntúa
0/46.8Resolución de issues — sin issues o sin datos
37.2/38.3Aceptación de PR — 37/38 PR decididos fusionados
0/15OpenSSF Scorecard: Code-Review — Found 0/25 approved changesets -- score normalized to 0
Datos de entrada utilizados
merged_prs37
open_issues0
closed_issues0
issue_closed_ratio
closed_unmerged_prs1
Excluidos de la puntuación (sin datos o no aplicable): Resolución de issues. Los pesos restantes se han renormalizado.
Cómo se puntúa
30/30Respaldo de la propiedad — propiedad de una organización
0/20Dominio verificado
3.4/25Alcance del propietario — 2 seguidores de Open-Tech-Foundation
23.8/25Trayectoria — 41 repos públicos, cuenta de ~7 años
Datos de entrada utilizados
followers2
owner_typeOrganization
is_verified
owner_loginOpen-Tech-Foundation
public_repos41
account_age_days2653
Cómo se puntúa
25/25Publicado y resoluble — 6 paquete(s) en npm
35/35Recencia de publicación — última publicación hace 4 días
20/20Historial de versiones — 22 versiones en el registro
20/20No obsoleto — activo, ni obsoleto ni retirado
Datos de entrada utilizados
packages@opentf/web, @opentf/web-cli, @opentf/web-docs, @opentf/web-form, @opentf/web-i18n, @opentf/web-test
ecosystemsnpm
any_deprecatedno
min_days_since_publish4

Calidad de Ingeniería

¿Existen unas prácticas mínimas de ingeniería y documentación?

74Bueno · 20% del índice global
Cómo se puntúa
24/24Flujos de trabajo de CI — 2 flujo(s) de trabajo
24/24Pruebas presentes
0/16Configuración de linter
0/9.6Hooks de pre-commit
0/6.4.editorconfig
16/20OpenSSF Scorecard: CI-Tests — 4 out of 5 merged PRs checked by a CI test -- score normalized to 8
Datos de entrada utilizados
has_ci
has_tests
has_editorconfigno
has_linter_configno
has_precommit_configno

Documentación

90Excelente
Cómo se puntúa
30/30README
25/25Directorio de documentación
15/15Sitio de documentación / página del proyecto — https://web.opentechf.org/
10/10Descripción del repositorio
10/10Topics — 8 topics
0/10Wiki
Datos de entrada utilizados
topicsapi, app, framework, jsx, reactive, signals, web, webcomponent
has_wikino
homepagehttps://web.opentechf.org/
has_readme
has_docs_dir
has_description

Seguridad

¿Son sólidas las prácticas visibles de seguridad y de cadena de suministro, sin exposición jurisdiccional de alto riesgo sin resolver?

30En riesgo · 16% del índice global
Cómo se puntúa
6/7.5Binary-Artifacts — binaries present in source code
0/7.5Branch-Protection — branch protection not enabled on development/release branches
2/2.5CI-Tests — 4 out of 5 merged PRs checked by a CI test -- score normalized to 8
0/2.5CII-Best-Practices — no effort to earn an OpenSSF best practices badge detected
0/7.5Code-Review — Found 0/25 approved changesets -- score normalized to 0
0/2.5Contributors — project has 0 contributing companies or organizations -- score normalized to 0
10/10Dangerous-Workflow — no dangerous workflow patterns detected
0/7.5Dependency-Update-Tool — no update tool detected
0/5Fuzzing — project is not fuzzed
2.5/2.5Licencia — license file detected
7.5/7.5Maintained — 30 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10
0/5Packaging — sin datos
0/5Pinned-Dependencies — dependency not pinned by hash detected -- score normalized to 0
0/5SAST — SAST tool is not run on all commits -- score normalized to 0
0/5Security-Policy — security policy file not detected
0/7.5Signed-Releases — sin datos
0/7.5Token-Permissions — detected GitHub workflow tokens with excessive permissions
0/7.5Vulnerabilities — 19 existing vulnerabilities detected
Datos de entrada utilizados
sourceopenssf_scorecard
checks_evaluated16
scorecard_versionv5.5.0
checks_inconclusive2
scorecard_aggregate3
Excluidos de la puntuación (sin datos o no aplicable): packaging, signed_releases. Los pesos restantes se han renormalizado.

Preparación para IA

¿Hasta qué punto está el repositorio preparado para desarrollarse y mantenerse con agentes de codificación de IA? Es una insignia independiente y experimental — peso 0,0, de modo que se presenta por separado y no afecta a la puntuación de salud global.

71Bueno · 0% del índice global
Cómo se puntúa
45/45Instrucciones para agentes — AGENTS.md
0/15Documentación legible por máquinas (llms.txt)
40/40Historial de commits legible — 100 de 100 commits humanos declaran su intención (asunto estructurado o cuerpo explicativo)
Datos de entrada utilizados
has_llms_txtno
legible_history_share1
agent_instruction_filesAGENTS.md
agent_instruction_max_bytes274
Cómo se puntúa
12.6/18Arranque con un solo comando — Cargo.toml, crates/otfw_cli/Cargo.toml, crates/otfw_compiler/Cargo.toml (convención del toolchain, sin ejecutor de tareas)
22/22Pruebas automatizadas
0/11Configuración de lint / formato
11/11Verificación estática de tipos — packages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json
10/10Entorno reproducible — lockfile
0/10Práctica demostrada con agentes — ningún commit con autoría de agente entre los últimos 100
0/8Mantenimiento automatizado — no se observan actualizaciones automáticas de dependencias
0/10OpenSSF Scorecard: Pinned-Dependencies — dependency not pinned by hash detected -- score normalized to 0
Datos de entrada utilizados
has_nixno
has_tests
lockfilesCargo.lock
has_dockerfileno
typed_languageno
bootstrap_files
has_devcontainerno
has_linter_configno
typecheck_configspackages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json
agent_commit_share0
toolchain_manifestsCargo.toml, crates/otfw_cli/Cargo.toml, crates/otfw_compiler/Cargo.toml, crates/otfw_ir/Cargo.toml
dependency_bot_commit_share0
Cómo se puntúa
27/45Código verificable por tipos — JavaScript con configuración de verificación de tipos (packages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json)
54.5/55Tamaños de archivo manejables — 3/326 archivos fuente de más de 60 KB
Datos de entrada utilizados
primary_languageJavaScript
largest_source_bytes139.665
source_files_sampled326
oversized_source_files3

Datos clave

0estrellas de GitHub
1contribuidores
596commits en los últimos 12 meses
4días desde el último push
100versiones publicadas
1factor bus
0issues abiertas
crates.io, npmecosistemas de paquetes

Advertencias de recopilación de datos

  • Could not fetch crates package 'otfw_ir' from its registry
  • Could not fetch crates package 'otfw_cli' from its registry
  • GitHub dependency-graph SBOM unavailable (404); the dependency graph may be disabled for this repository

Más detalle

OpenSSF Scorecard 3.0 / 10
3.0agregado

Evaluación de seguridad independiente y agnóstica en cuanto a herramientas, procedente del proyecto de código abierto OpenSSF Scorecard. Cada comprobación premia una práctica de seguridad, no la herramienta de un proveedor concreto. Las comprobaciones que Scorecard no pudo determinar se marcan como n/d y se excluyen de la puntuación de seguridad (nunca se cuentan como cero).Scorecard v5.5.0 · 2026-07-23 21:57 UTC

8Binary-Artifactsbinaries present in source code
0Branch-Protectionbranch protection not enabled on development/release branches
8CI-Tests4 out of 5 merged PRs checked by a CI test -- score normalized to 8
0CII-Best-Practicesno effort to earn an OpenSSF best practices badge detected
0Code-ReviewFound 0/25 approved changesets -- score normalized to 0
0Contributorsproject has 0 contributing companies or organizations -- score normalized to 0
10Dangerous-Workflowno dangerous workflow patterns detected
0Dependency-Update-Toolno update tool detected
0Fuzzingproject is not fuzzed
10Licenselicense file detected
10Maintained30 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10
n/dPackagingpackaging workflow not detected
0Pinned-Dependenciesdependency not pinned by hash detected -- score normalized to 0
0SASTSAST tool is not run on all commits -- score normalized to 0
0Security-Policysecurity policy file not detected
n/dSigned-Releasesno releases found
0Token-Permissionsdetected GitHub workflow tokens with excessive permissions
0Vulnerabilities19 existing vulnerabilities detected
Dependencias directas 28
RegistroPaqueteRestricción de versiónManifiesto
npm@opentf/webworkspace:*playground/package.json
npm@opentf/web-formworkspace:*playground/package.json
npmmonaco-editor^0.52.2playground/package.json
npm@monaco-editor/loader^1.4.0playground/package.json
npmprismjs^1.29.0playground/package.json
npmzod^4.3.6playground/package.json
npm@opentf/web^0.20.0website/package.json
npm@opentf/web-docs^0.17.0website/package.json
npm@opentf/web-form^1.15.0website/package.json
npm@opentf/web-i18n^1.15.0website/package.json
crates.iootfw_compilercrates/otfw_cli/Cargo.toml
crates.iomarkdown1.0.0crates/otfw_compiler/Cargo.toml
crates.iootfw_ircrates/otfw_compiler/Cargo.toml
crates.iooxccrates/otfw_compiler/Cargo.toml
crates.iosyntect5crates/otfw_compiler/Cargo.toml
npmkolorist^1.8.0packages/create-web/package.json
npmprompts^2.4.2packages/create-web/package.json
npm@opentf/web-compiler0.10.0packages/web-cli/package.json
npm@tailwindcss/node4.2.2packages/web-cli/package.json
npm@tailwindcss/oxide4.2.2packages/web-cli/package.json
npmrolldown1.0.0-rc.17packages/web-cli/package.json
npmtailwindcss4.2.2packages/web-cli/package.json
npmpagefind^1.5.2packages/web-docs/package.json
npm@opentf/std^1.0.0-beta.2packages/web-form/package.json
npmintl-messageformat^10.7.0packages/web-i18n/package.json
npm@testing-library/dom^10.4.1packages/web-test/package.json
npm@testing-library/user-event^14.6.1packages/web-test/package.json
npmhappy-dom^20.9.0packages/web-test/package.json
Todas las dependencias no recopilado

No fue posible recopilar el conjunto de dependencias resuelto para este informe: GitHub dependency-graph SBOM unavailable (404); the dependency graph may be disabled for this repository

Informe JSON sin procesar legible por máquina
{
  "data": {
    "repo": {
      "topics": [
        "api",
        "app",
        "framework",
        "jsx",
        "reactive",
        "signals",
        "web",
        "webcomponent"
      ],
      "is_fork": false,
      "size_kb": 2299,
      "has_wiki": false,
      "homepage": "https://web.opentechf.org/",
      "languages": {
        "CSS": 77599,
        "MDX": 235937,
        "HTML": 21396,
        "Rust": 496709,
        "Svelte": 3600,
        "JavaScript": 1082784
      },
      "pushed_at": "2026-07-19T06:20:26Z",
      "created_at": "2026-04-19T15:32:49Z",
      "owner_type": "Organization",
      "updated_at": "2026-07-19T06:20:04Z",
      "description": "A high-performance, zero-VDOM framework that compiles JSX to native DOM using signals and standard Web Components.",
      "is_archived": false,
      "is_disabled": false,
      "license_spdx": "MIT",
      "default_branch": "main",
      "license_spdx_raw": "MIT",
      "primary_language": "JavaScript",
      "significant_languages": [
        "JavaScript",
        "Rust",
        "MDX"
      ]
    },
    "owner": {
      "blog": "https://opentechf.org",
      "name": "Open Tech Foundation",
      "type": "Organization",
      "login": "Open-Tech-Foundation",
      "company": null,
      "location": null,
      "followers": 2,
      "avatar_url": "https://avatars.githubusercontent.com/u/49762721?v=4",
      "created_at": "2019-04-18T17:28:48Z",
      "is_verified": null,
      "public_repos": 41,
      "account_age_days": 2653
    },
    "license": {
      "state": "standard",
      "spdx_id": "MIT",
      "raw_spdx": "MIT",
      "file_present": true,
      "scorecard_found": true,
      "profile_has_license": true
    },
    "activity": {
      "releases": [
        {
          "tag": "@opentf/web-cli@1.18.0",
          "kind": "other",
          "published_at": "2026-07-19T06:20:27Z"
        },
        {
          "tag": "@opentf/web-cli@1.17.0",
          "kind": "other",
          "published_at": "2026-07-18T20:51:12Z"
        },
        {
          "tag": "@opentf/web-i18n@1.15.0",
          "kind": "other",
          "published_at": "2026-07-18T14:12:56Z"
        },
        {
          "tag": "@opentf/web-form@1.15.0",
          "kind": "other",
          "published_at": "2026-07-18T14:12:53Z"
        },
        {
          "tag": "@opentf/web-docs@0.17.0",
          "kind": "other",
          "published_at": "2026-07-18T14:12:49Z"
        },
        {
          "tag": "@opentf/web-cli@1.16.0",
          "kind": "other",
          "published_at": "2026-07-18T14:12:45Z"
        },
        {
          "tag": "@opentf/web-test@1.15.0",
          "kind": "other",
          "published_at": "2026-07-18T14:12:41Z"
        },
        {
          "tag": "@opentf/web@0.20.0",
          "kind": "other",
          "published_at": "2026-07-18T14:12:37Z"
        },
        {
          "tag": "@opentf/web-i18n@1.14.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:52Z"
        },
        {
          "tag": "@opentf/web-form@1.14.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:49Z"
        },
        {
          "tag": "@opentf/web-docs@0.16.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:45Z"
        },
        {
          "tag": "@opentf/web-cli@1.15.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:41Z"
        },
        {
          "tag": "@opentf/web-test@1.14.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:37Z"
        },
        {
          "tag": "@opentf/web-compiler@0.10.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:34Z"
        },
        {
          "tag": "@opentf/web@0.19.0",
          "kind": "other",
          "published_at": "2026-07-18T05:50:30Z"
        },
        {
          "tag": "@opentf/web-docs@0.15.0",
          "kind": "other",
          "published_at": "2026-07-08T22:15:49Z"
        },
        {
          "tag": "@opentf/web-i18n@1.13.0",
          "kind": "other",
          "published_at": "2026-07-08T16:45:39Z"
        },
        {
          "tag": "@opentf/web-form@1.13.0",
          "kind": "other",
          "published_at": "2026-07-08T16:45:35Z"
        },
        {
          "tag": "@opentf/web-docs@0.14.0",
          "kind": "other",
          "published_at": "2026-07-08T16:45:31Z"
        },
        {
          "tag": "@opentf/web-cli@1.14.0",
          "kind": "other",
          "published_at": "2026-07-08T16:45:27Z"
        },
        {
          "tag": "@opentf/web-test@1.13.0",
          "kind": "other",
          "published_at": "2026-07-08T16:45:23Z"
        },
        {
          "tag": "@opentf/web@0.18.0",
          "kind": "other",
          "published_at": "2026-07-08T16:45:19Z"
        },
        {
          "tag": "@opentf/web-cli@1.13.1",
          "kind": "other",
          "published_at": "2026-07-08T11:15:49Z"
        },
        {
          "tag": "@opentf/web-compiler@0.9.0",
          "kind": "other",
          "published_at": "2026-07-08T11:15:45Z"
        },
        {
          "tag": "@opentf/create-web@0.16.0",
          "kind": "other",
          "published_at": "2026-07-08T11:15:40Z"
        },
        {
          "tag": "@opentf/create-web@0.15.0",
          "kind": "other",
          "published_at": "2026-07-08T11:13:47Z"
        },
        {
          "tag": "@opentf/web-i18n@1.12.0",
          "kind": "other",
          "published_at": "2026-07-08T06:41:46Z"
        },
        {
          "tag": "@opentf/web-form@1.12.0",
          "kind": "other",
          "published_at": "2026-07-08T06:41:43Z"
        },
        {
          "tag": "@opentf/web-docs@0.13.0",
          "kind": "other",
          "published_at": "2026-07-08T06:41:39Z"
        },
        {
          "tag": "@opentf/web-cli@1.13.0",
          "kind": "other",
          "published_at": "2026-07-08T06:41:35Z"
        },
        {
          "tag": "@opentf/web-test@1.12.0",
          "kind": "other",
          "published_at": "2026-07-08T06:41:32Z"
        },
        {
          "tag": "@opentf/web@0.17.0",
          "kind": "other",
          "published_at": "2026-07-08T06:41:28Z"
        },
        {
          "tag": "@opentf/web-i18n@1.11.0",
          "kind": "other",
          "published_at": "2026-07-07T22:00:38Z"
        },
        {
          "tag": "@opentf/web-form@1.11.0",
          "kind": "other",
          "published_at": "2026-07-07T22:00:35Z"
        },
        {
          "tag": "@opentf/web-docs@0.12.0",
          "kind": "other",
          "published_at": "2026-07-07T22:00:31Z"
        },
        {
          "tag": "@opentf/web-cli@1.12.0",
          "kind": "other",
          "published_at": "2026-07-07T22:00:27Z"
        },
        {
          "tag": "@opentf/web-test@1.11.0",
          "kind": "other",
          "published_at": "2026-07-07T22:00:23Z"
        },
        {
          "tag": "@opentf/web@0.16.0",
          "kind": "other",
          "published_at": "2026-07-07T22:00:19Z"
        },
        {
          "tag": "@opentf/web-i18n@1.10.0",
          "kind": "other",
          "published_at": "2026-07-07T21:41:43Z"
        },
        {
          "tag": "@opentf/web-form@1.10.0",
          "kind": "other",
          "published_at": "2026-07-07T21:41:38Z"
        },
        {
          "tag": "@opentf/web-docs@0.11.0",
          "kind": "other",
          "published_at": "2026-07-07T21:41:34Z"
        },
        {
          "tag": "@opentf/web-cli@1.11.0",
          "kind": "other",
          "published_at": "2026-07-07T21:41:29Z"
        },
        {
          "tag": "@opentf/web-test@1.10.0",
          "kind": "other",
          "published_at": "2026-07-07T21:41:24Z"
        },
        {
          "tag": "@opentf/web@0.15.0",
          "kind": "other",
          "published_at": "2026-07-07T21:41:20Z"
        },
        {
          "tag": "@opentf/web-cli@1.10.0",
          "kind": "other",
          "published_at": "2026-07-07T20:46:20Z"
        },
        {
          "tag": "@opentf/web-compiler@0.8.0",
          "kind": "other",
          "published_at": "2026-07-07T20:46:16Z"
        },
        {
          "tag": "@opentf/web-i18n@1.9.0",
          "kind": "other",
          "published_at": "2026-07-07T19:30:41Z"
        },
        {
          "tag": "@opentf/web-form@1.9.0",
          "kind": "other",
          "published_at": "2026-07-07T19:30:37Z"
        },
        {
          "tag": "@opentf/web-docs@0.10.0",
          "kind": "other",
          "published_at": "2026-07-07T19:30:33Z"
        },
        {
          "tag": "@opentf/web-cli@1.9.0",
          "kind": "other",
          "published_at": "2026-07-07T19:30:29Z"
        },
        {
          "tag": "@opentf/web-test@1.9.0",
          "kind": "other",
          "published_at": "2026-07-07T19:30:25Z"
        },
        {
          "tag": "@opentf/web@0.14.0",
          "kind": "other",
          "published_at": "2026-07-07T19:30:21Z"
        },
        {
          "tag": "@opentf/web-cli@1.8.1",
          "kind": "other",
          "published_at": "2026-07-07T12:41:44Z"
        },
        {
          "tag": "@opentf/web-compiler@0.7.0",
          "kind": "other",
          "published_at": "2026-07-07T12:41:40Z"
        },
        {
          "tag": "@opentf/web-i18n@1.8.0",
          "kind": "other",
          "published_at": "2026-07-07T07:31:07Z"
        },
        {
          "tag": "@opentf/web-form@1.8.0",
          "kind": "other",
          "published_at": "2026-07-07T07:31:03Z"
        },
        {
          "tag": "@opentf/web-docs@0.9.0",
          "kind": "other",
          "published_at": "2026-07-07T07:30:58Z"
        },
        {
          "tag": "@opentf/web-cli@1.8.0",
          "kind": "other",
          "published_at": "2026-07-07T07:30:54Z"
        },
        {
          "tag": "@opentf/web-test@1.8.0",
          "kind": "other",
          "published_at": "2026-07-07T07:30:49Z"
        },
        {
          "tag": "@opentf/web@0.13.0",
          "kind": "other",
          "published_at": "2026-07-07T07:30:45Z"
        },
        {
          "tag": "@opentf/web-i18n@1.7.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:25Z"
        },
        {
          "tag": "@opentf/web-form@1.7.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:21Z"
        },
        {
          "tag": "@opentf/web-docs@0.8.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:17Z"
        },
        {
          "tag": "@opentf/web-cli@1.7.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:14Z"
        },
        {
          "tag": "@opentf/web-test@1.7.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:10Z"
        },
        {
          "tag": "@opentf/web@0.12.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:06Z"
        },
        {
          "tag": "@opentf/create-web@0.14.0",
          "kind": "other",
          "published_at": "2026-07-06T20:34:03Z"
        },
        {
          "tag": "@opentf/web-i18n@1.6.0",
          "kind": "other",
          "published_at": "2026-07-06T09:38:17Z"
        },
        {
          "tag": "@opentf/web-form@1.6.0",
          "kind": "other",
          "published_at": "2026-07-06T09:38:13Z"
        },
        {
          "tag": "@opentf/web-docs@0.7.0",
          "kind": "other",
          "published_at": "2026-07-06T09:38:09Z"
        },
        {
          "tag": "@opentf/web-cli@1.6.0",
          "kind": "other",
          "published_at": "2026-07-06T09:38:05Z"
        },
        {
          "tag": "@opentf/web-test@1.6.0",
          "kind": "other",
          "published_at": "2026-07-06T09:38:01Z"
        },
        {
          "tag": "@opentf/web-compiler@0.6.0",
          "kind": "other",
          "published_at": "2026-07-06T09:37:57Z"
        },
        {
          "tag": "@opentf/web@0.11.0",
          "kind": "other",
          "published_at": "2026-07-06T09:37:53Z"
        },
        {
          "tag": "@opentf/web-i18n@1.5.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:34Z"
        },
        {
          "tag": "@opentf/web-form@1.5.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:30Z"
        },
        {
          "tag": "@opentf/web-docs@0.6.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:26Z"
        },
        {
          "tag": "@opentf/web-cli@1.5.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:22Z"
        },
        {
          "tag": "@opentf/web-test@1.5.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:18Z"
        },
        {
          "tag": "@opentf/web-compiler@0.5.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:14Z"
        },
        {
          "tag": "@opentf/web@0.10.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:09Z"
        },
        {
          "tag": "@opentf/create-web@0.13.0",
          "kind": "other",
          "published_at": "2026-07-05T22:39:06Z"
        },
        {
          "tag": "@opentf/create-web@0.12.0",
          "kind": "other",
          "published_at": "2026-07-05T16:10:34Z"
        },
        {
          "tag": "@opentf/create-web@0.11.0",
          "kind": "other",
          "published_at": "2026-07-05T15:23:20Z"
        },
        {
          "tag": "@opentf/web-i18n@1.4.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:30Z"
        },
        {
          "tag": "@opentf/web-form@1.4.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:26Z"
        },
        {
          "tag": "@opentf/web-docs@0.5.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:22Z"
        },
        {
          "tag": "@opentf/web-cli@1.4.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:18Z"
        },
        {
          "tag": "@opentf/web-test@1.4.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:14Z"
        },
        {
          "tag": "@opentf/web-compiler@0.4.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:10Z"
        },
        {
          "tag": "@opentf/web@0.9.0",
          "kind": "other",
          "published_at": "2026-07-05T15:05:05Z"
        },
        {
          "tag": "@opentf/create-web@0.10.0",
          "kind": "other",
          "published_at": "2026-07-05T08:08:36Z"
        },
        {
          "tag": "@opentf/web-cli@1.3.1",
          "kind": "other",
          "published_at": "2026-07-05T08:02:56Z"
        },
        {
          "tag": "@opentf/web-compiler@0.3.0",
          "kind": "other",
          "published_at": "2026-07-05T08:02:52Z"
        },
        {
          "tag": "@opentf/create-web@0.9.0",
          "kind": "other",
          "published_at": "2026-07-05T07:40:08Z"
        },
        {
          "tag": "@opentf/web-i18n@1.3.0",
          "kind": "other",
          "published_at": "2026-07-05T06:59:23Z"
        },
        {
          "tag": "@opentf/web-form@1.3.0",
          "kind": "other",
          "published_at": "2026-07-05T06:59:20Z"
        },
        {
          "tag": "@opentf/web-docs@0.4.0",
          "kind": "other",
          "published_at": "2026-07-05T06:59:17Z"
        },
        {
          "tag": "@opentf/web-cli@1.3.0",
          "kind": "other",
          "published_at": "2026-07-05T06:59:13Z"
        },
        {
          "tag": "@opentf/web-test@1.3.0",
          "kind": "other",
          "published_at": "2026-07-05T06:59:09Z"
        }
      ],
      "recent_commits": [
        {
          "oid": "ec0b269b5901225e8c3dfbffaf9818fa47051734",
          "body": "chore(release): @opentf/web-cli@1.18.0",
          "is_bot": false,
          "headline": "Merge pull request #38 from Open-Tech-Foundation/release/2026-07-19",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-19T06:19:53Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "590d5a944d2b1a7ddab25f970a39a6d1cd5bd939",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.18.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-19T06:19:25Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "eda5ee6dd663ffc7a2d2b05d0868e2e5dd0777ec",
          "body": "The release stamped [Unreleased] to [1.17.0]; the newer dev symlinked-dependency\nworker/asset fix was left inside that already-published section. Move it to the\nnew [Unreleased] so 1.17.0 lists only what shipped in it.",
          "is_bot": false,
          "headline": "docs(web-cli): move dev symlinked-dep worker fix to [Unreleased]",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-19T06:18:48Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "5475dc0e84ecfef0489bc57e9b0a8af65ed85e1a",
          "body": "…utside root)\n\nThe /__worker/ and /__asset/ dev handlers gated the decoded file path with a\nroot-containment check, so a worker/asset reached through a symlinked node_modules\ndependency (workspace/isolated install) — whose real path resolves outside the\nproject root — was refused and 404'd in dev, t\n[…]\nghter than the old guard: a never-emitted/crafted URL is still refused.\n\nLock it with a worker-dep/ fixture symlinked into the app's node_modules at test\ntime (its real path outside the fixture root).",
          "is_bot": false,
          "headline": "fix(web-cli): serve dev worker/asset from symlinked deps (real path o…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-19T06:17:11Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ffe7110dcd9ee6638e1fa25640cc138b0ad3e8a8",
          "body": "chore(release): @opentf/web-cli@1.17.0",
          "is_bot": false,
          "headline": "Merge pull request #37 from Open-Tech-Foundation/release/2026-07-18",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T18:08:47Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "c82b3236fb9aab52bfaf9ec77aaa96190ca72fed",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.17.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T18:07:53Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "6b4c5e881648f37e8c5a3368007592669456371d",
          "body": "Decouple the @opentf/web-compiler (Rust binary, cross-platform build\nmatrix) release from the pure-JS packages so a JS-only release no longer\nwaits on the compiler matrix.\n\n- check-release now emits two flags: should_release (non-compiler packages,\n  --exclude-package @opentf/web-compiler) and relea\n[…]\n\n- Add a `release` concurrency group (cancel-in-progress: false) to serialize\n  release runs, `id-token: write` for npm provenance, and drop the dead\n  Windows install steps from the ubuntu-only jobs.",
          "is_bot": false,
          "headline": "ci(release): split web-compiler and JS publish tracks",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T17:56:54Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ab4f98a2a830b6a5df0bd38105764e3142de2a5d",
          "body": "… 404)\n\nRoot cause of the real-world report: workerAssetsPlugin deduped emitted\nfiles by path but chose chunk-vs-asset from whichever reference was scanned\nfirst. A worker script also referenced as a bare new URL (a prefetch/preload\nlink) that was seen first got emitted as a verbatim {type:\"asset\"} \n[…]\n fixture references the worker as a bare new URL\n  *before* new Worker (asset-first, the trigger), so the existing nested-emit\n  assertions now guard the regression (verified they fail on old 1.16.0).",
          "is_bot": false,
          "headline": "fix(web-cli): never downgrade a worker to a copied asset (nested refs…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T16:44:57Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "9a2f3553018434800379f1ccbb28964b5b69e486",
          "body": "workerAssetsPlugin resolved each new URL(…, import.meta.url) with a naive\ndirname(importer)+spec existsSync check and, on a miss, dropped the reference\nsilently — so a worker/asset that isn't a literal on-disk sibling (symlinked\nnode_modules, a package exports map, an extensionless specifier) was le\n[…]\nd worker chunks was already correct (verified: nested\nworkers and assets-inside-workers emit through real otfw build) — this makes a\ngenuine resolution failure visible instead of a silent runtime 404.",
          "is_bot": false,
          "headline": "fix(web-cli): resolve worker/asset refs via Rolldown; warn on misses",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T16:22:38Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "c5762cb521cf3f52facb118e8d6c82cefb30d6f9",
          "body": "The recursion re-scans emitted worker chunks for their own `new URL`\nreferences, but only nested *workers* were asserted — not a bare asset URL\ninside a worker (the kernel-worker → wasm case from the report).\n\n- unit: a worker whose body does `new URL(\"./kernel.wasm\", …)` emits both the\n  worker chu\n[…]\n(csr/ssg) the\n  hashed kernel-*.wasm is emitted and the worker chunk points at it with no\n  dangling literal, and (dev) the worker bundle rewrites it to a /__asset/ URL\n  that serves application/wasm.",
          "is_bot": false,
          "headline": "test(web-cli): cover assets referenced from inside a worker chunk",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T16:04:06Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "68b8d4e6b9daf8f5eceefbd171c04b5550b71765",
          "body": "Remove `website` from the root workspaces so it no longer resolves\n`@opentf/*` via workspace symlinks, and give it a standalone `bun.lock`\npinned to the published releases (web@0.20.0, web-cli@1.16.0,\nweb-docs@0.17.0, web-form@1.15.0, web-i18n@1.15.0). `bun install` now runs\nin website/ against the registry, so the site is built and previewed exactly\nas an external consumer would. `@opentf/web-compiler` is trusted so its\npostinstall fetches the otfwc binary.",
          "is_bot": false,
          "headline": "chore(website): develop in isolation with its own lockfile",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T15:38:39Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "9b7d7371a8e583e085dfe572658305fd01135a7b",
          "body": "Document the `new Worker(new URL(…, import.meta.url))` + `new URL(…,\nimport.meta.url)` asset convention now handled by @opentf/web-cli@1.16.0\nacross dev, build, and --ssg.\n\n- New Core Concepts → \"Assets & Workers\" page: static assets (.wasm, images),\n  module + shared + nested workers, the static-re\n[…]\ne lists the emitted worker/asset outputs and links the\n  new guide.\n- Align the docs version badge with @opentf/web@0.20.0 and bump the website's\n  @opentf/* dependency ranges to the current releases.",
          "is_bot": false,
          "headline": "docs(website): add Assets & Workers guide; bump framework to v0.20.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T15:30:54Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "5b5827023f26fc14a375e53a1495a7b4e1a4c88b",
          "body": "chore(release): @opentf/web-cli@1.16.0, @opentf/web@0.20.0",
          "is_bot": false,
          "headline": "Merge pull request #36 from Open-Tech-Foundation/release/2026-07-18",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T14:08:31Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "332c959eb33dcefc6a391f706de836850f916e41",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.16.0, @opentf/web@0.20.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T14:08:00Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "34d12f4dab61655eb6ae024391ddd7b3bef5bd7c",
          "body": "Backfills the [Unreleased] entry the release preflight requires for the\none test-only commit (1d8709f) landed since @opentf/web@0.19.0.",
          "is_bot": false,
          "headline": "docs(web): changelog for SSG render-suite test isolation",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T14:06:44Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "ebda214413a654593b71bf9a4d2ad67f118c9579",
          "body": "Rolldown left `new Worker(new URL(\"./w.js\", import.meta.url))` and bare\n`new URL(\"./x.wasm\", import.meta.url)` references as dangling runtime\nstrings, so the worker/asset file was never produced and 404'd at runtime\n(import.meta.url resolved the literal against the bundle's own hashed URL).\n\n- share\n[…]\n normalized and guarded to the project root.\n- tests: unit test driving the plugin through real Rolldown, plus a\n  csr/ssg/dev e2e with a worker fixture (nested workers, wasm MIME,\n  traversal guard).",
          "is_bot": false,
          "headline": "fix(web-cli): emit web workers and new URL assets in build/dev/ssg",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T14:04:59Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "1d8709ff67eb19bb9fd215e710f31b8bb34ec1ee",
          "body": "`server/render.test.js` reset the shared route-table singleton only in afterEach,\nso its first test inherited whatever a sibling suite left behind. When bun ran a\nroute-registering file (e.g. router.test.js, which composes a root layout and\nnever cleans up) before it, a leftover layout wrapped the r\n[…]\n flaky under CI's bun test-file ordering, green\nlocally. Reset the routes in beforeEach too so the suite is isolated regardless of\norder. Reproduced deterministically by pre-registering a root layout.",
          "is_bot": false,
          "headline": "test(web): isolate SSG render suite from shared-route pollution",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T06:14:12Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "50248496c42093b9ecd0e6f97f2fea9c6ca59c23",
          "body": "The release bumped @opentf/web-cli's dependency on @opentf/web-compiler to\n0.10.0 in package.json but left bun.lock recording 0.8.0. CI runs `bun install`\nwith CI=true (frozen lockfile), which rejects the package.json↔lockfile drift —\nso CI fails at install before any test runs, even though every suite passes\nlocally. Regenerate the lockfile entry to 0.10.0.",
          "is_bot": false,
          "headline": "fix(repo): sync bun.lock with web-cli's bumped web-compiler dependency",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T05:54:29Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "af75b9ed75c9bca6ae4e202f46df79cf27d07efc",
          "body": "chore(release): @opentf/web-cli@1.15.0, @opentf/web-compiler@0.10.0, …",
          "is_bot": false,
          "headline": "Merge pull request #35 from Open-Tech-Foundation/release/2026-07-18",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T05:46:32Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "601a1e2ac05b9c3199967ccb12a042c4a681c3b1",
          "body": "…@opentf/web@0.19.0",
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.15.0, @opentf/web-compiler@0.10.0, …",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T05:45:58Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "ecbb70990a43f92291c0bdc558dfe45ac553e469",
          "body": "Re-applies the [Unreleased] entry (was in c752fc0, dropped when the branch was\nreset to 5dd6857). The otfwc codegen fix (crates/otfw_compiler) ships to users as\nthe prebuilt binary in @opentf/web-compiler, so its user-facing entry belongs here\nand the release must pick it up (alongside bumping web-cli's pinned dependency).",
          "is_bot": false,
          "headline": "docs(web-compiler): changelog for JSX-value-local hydration (Phase 2.1e)",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T05:44:29Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "5dd685750466338161d3404afc8938cd82b4d82e",
          "body": "Records the web-cli half of the keyless-list reorder warning (ca5ed3d): `otfw\ndev`/`otfw build` now define process.env.NODE_ENV so the runtime's dev-only\ndiagnostics run in dev and compile away in production. Fills the empty\n[Unreleased] section the release preflight flagged.",
          "is_bot": false,
          "headline": "docs(web-cli): changelog for NODE_ENV define gating dev diagnostics",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T05:31:14Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "b19eb251970fc750792abe214f3b1ab5e7efee09",
          "body": "The docs-layout idiom — `const body = <jsx>; return frame ? <shell>{body}</shell>\n: body` — was not adoptable by the hydrate backend: it reported \"JSX-as-value is\nnot supported\", demoting the whole view to RebuildIfServerChildren. On first\nnavigation to a docs page that discarded the server DOM (a c\n[…]\nape wrapping <Tree> → <Link>,\nadopting in place with its nested islands), alongside a still-non-adoptable <Panel>\nthat keeps guarding the runBuild cascade. Full cargo/bun suites + 75 e2e checks green.",
          "is_bot": false,
          "headline": "fix(compiler): hydrate JSX-value locals in place (const body = <jsx>)",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-18T05:24:24Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ff4482d1f8d8f53e2380126c12bedd2db9508dd1",
          "body": "`$state` holds a signal whose value is replaced, never mutated, so writing a\nfield of an item is a silent no-op (SPEC §5.4.4's List Reactivity Matrix pins\nthis: \"mutate items[0].active directly ❌\"). The diagnostic that explains this\nonly fired when the member root was the `$state` symbol itself, so \n[…]\nflags writes through them, pointing at `reactive()`.\nAliases taken off a call are left untracked: the receiver is a fresh value, so\nmutating it loses nothing and flagging it would be a false positive.",
          "is_bot": false,
          "headline": "fix(compiler): catch $state mutation through aliases and callback params",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-15T15:27:17Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ca5ed3d7372e7c502135bdb2e016d8710f6fe6cc",
          "body": "`bindList` falls back to index keying when no `key` is given (SPEC §5.4.4).\nThat matches items by position, so splicing out a middle item shifts every\nlater item up a slot: the reconciler re-points each surviving node at its\nneighbour's data and removes the node at the *tail*. Bindings re-render, wh\n[…]\nNODE_ENV` in both bundling paths: \"development\" in `otfw\ndev`, \"production\" in `otfw build`, where minification then drops the branch\n(verified: the warning text is absent from the production bundle).",
          "is_bot": false,
          "headline": "fix(web): warn when a keyless list reorders under the index fallback",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-15T15:22:30Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "71ee5204ab809ea8613239f58f6ff8ab42e1ab37",
          "body": "chore(release): @opentf/web-docs@0.15.0",
          "is_bot": false,
          "headline": "Merge pull request #34 from Open-Tech-Foundation/release/2026-07-08",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T22:11:51Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "16591bdae715318e41fe568645316450afe935f5",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-docs@0.15.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T22:11:33Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "a8c4068a10a4752df9afccc01b1572cf11d3c944",
          "body": null,
          "is_bot": false,
          "headline": "docs(web-docs): changelog for collapsible sidebar groups",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T22:09:37Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "861f7e84b8bdd7ff2fcffb8d7904911e8fa65990",
          "body": "A fresh Sidebar mounts scrolled to the top on navigation, so in a long\nnav tree the active link landed off-screen. An effect keyed on\nrouter.pathname now brings the active item into the sidebar's own scroll\nviewport when it's out of view — adjusting only the sidebar's scrollTop,\nnever the page scroll, and only when needed. Covered by the browser e2e\n(overflowing tree + deep route).",
          "is_bot": false,
          "headline": "fix(web-docs): scroll the active sidebar item into view after navigation",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T22:04:53Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "0fd82bce49aea2a15305a1d488a23037b7b668a9",
          "body": "A section that is also its own page (e.g. Deployment, which has a\npage.mdx plus children) rendered its chevron on the right, while\nlabel-only sections put it on the left — an inconsistent split. Move the\nchevron ahead of the link so every group's chevron left-aligns in one\ncolumn, and drop the now-redundant leading dot on linked groups.",
          "is_bot": false,
          "headline": "fix(web-docs): left-align the collapse chevron for linked sidebar groups",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T21:53:58Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "c39f3055951b6b58687bd3a628678ed82c2533cc",
          "body": "Drives headless Chromium (like mobile-drawer.mjs) to cover the CSS the\nhappy-dom unit tests can't: the chevron rotation on .is-open, the child\nlist gaining layout height when a group expands, the collapsed group\nabsent from the DOM, active-branch auto-expand on load, and the\nreduced-motion transitio\n[…]\nidebar-chevron was placed before the chevron's transition rule,\nso source order (media queries add no specificity) let the transition\nwin — the override never applied. Moved it after the chevron rule.",
          "is_bot": false,
          "headline": "test(web-docs): browser e2e for collapsible sidebar groups",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T21:34:48Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "8aa11bc26635f38379b013dfa2e437a0f0e8f9dc",
          "body": "Groups with children now render a chevron toggle instead of always showing\ntheir child list. The branch containing the active route stays open and\ntop-level groups start expanded; open/closed state is per-session (no\npersistence). aria-controls ids come from a deterministic position path so\nthey're collision-free and hydration-safe.",
          "is_bot": false,
          "headline": "feat(web-docs): collapsible sidebar nav groups",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T21:26:25Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "9bbdeeeae2d73b04e07d6370c93cd7628330d001",
          "body": "Split SPA vs Fullstack trees, document public/ and otfw.config.js at the\nproject root, and extend the special-files table with route loaders, _meta.js,\nand dist/ output.",
          "is_bot": false,
          "headline": "docs(website): expand Project Structure for SPA, loaders, and public/",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:42:38Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "47441cb6e20dad253d473a767b3b264e24e9da86",
          "body": "chore(release): @opentf/web-cli@1.14.0, @opentf/web@0.18.0",
          "is_bot": false,
          "headline": "Merge pull request #33 from Open-Tech-Foundation/release/2026-07-08",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:41:01Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "41d95081079cedcb4a0a9817fafd1b35968c93ab",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.14.0, @opentf/web@0.18.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:39:18Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "630e801415c7765c51a8fabc0c4b03e2abb55cc3",
          "body": "Add a Troubleshooting page covering init-once JSX, signal mutation, hydration,\ncompile errors, the dev overlay, and SEO/metadata gotchas. Wire Metadata & SEO\ninto the routing sidebar and link from Pages & Layouts, Dynamic Routes, Build,\nand Static Generation. Align troubleshooting and routing copy with CSR layout-head\ninjection and per-route SSG/SSR requirements.",
          "is_bot": false,
          "headline": "docs(website): add Troubleshooting guide and wire metadata cross-links",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:37:58Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "410229deb0ed99d236ef01e98ee7adba138a0fbd",
          "body": "Replaces the throwaway verification harness with a real, wired-in e2e\n(build-metadata.mjs) run from test:e2e. Adds route-independent metadata to the\nshared fixture's root layout and asserts, against actual dist/ output:\n- plain CSR injects layout favicon/description/OG + feed alternate (links[].type)\n  into the shell, with no route-specific canonical/title;\n- --ssg gives /about its page title, a per-route canonical, and the inherited\n  feed alternate.",
          "is_bot": false,
          "headline": "test(web-cli): committed e2e for CSR + SSG metadata head composition",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:35:29Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "13cf788ed9c030e24d6fa1454a8372182769e6a7",
          "body": "…layout metadata",
          "is_bot": false,
          "headline": "docs(changelog): links[].type fix, route-independent renderHead, CSR …",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:30:09Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "85fc578b1bd473ee5a83a4e963b848b888e527f9",
          "body": "…verEntrySource export)",
          "is_bot": false,
          "headline": "test: cover CSR layout-head contract (resolveMetadata entry:null, ser…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:30:09Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "157c72aa18a2bfd5605541f4383a1561868fc165",
          "body": "Plain CSR now injects the root layout's site-wide metadata into index.html;\nper-page title/canonical/generateMetadata still need --ssg or otfw serve.",
          "is_bot": false,
          "headline": "docs(website): describe CSR layout-metadata injection",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:17:13Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "e30ac997ed1c1522a3c999b499bd88a21c200225",
          "body": "Plain `otfw build` (CSR) previously wrote index.html as a bare shell and\nignored metadata exports entirely, so a favicon/description declared in the\nroot layout never reached the document. A CSR SPA serves one index.html for\nevery route, so the build now resolves the root layout chain's\nroute-indepe\n[…]\nthem.\n- resolveLayoutShellHead compiles just the root layout (SSG backend) and\n  renders its head; wired into runBuild for the CSR path only (!hydrate).\n  SSG/SSR keep injecting a full per-route head.",
          "is_bot": false,
          "headline": "feat(web): inject root layout metadata into plain CSR shell",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T16:17:03Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "1cb0dc708f325c6a3e84729720ec1641e7d4f050",
          "body": "- Plain `otfw build` (CSR) ignores metadata exports entirely; the\n  table wrongly claimed layout links still apply.\n- Document links[].type (feed alternates) now that renderHead emits it.\n- Show plain otfw.config.js export for SPA/fullstack; defineDocsConfig\n  is docs-only.\n- Note dynamic routes without getStaticPaths still get per-request SSR\n  metadata, and twitter card auto-upgrade behavior.",
          "is_bot": false,
          "headline": "docs(website): correct metadata CSR behavior and config examples",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T15:47:47Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "ee08ea5ba6aa32476150ed5755ba3151acad1086",
          "body": "RSS/feed alternates declared via metadata.links carried a `type`\n(e.g. application/rss+xml) that renderHead silently dropped, so the\ngenerated <link> lacked its MIME type. Emit it alongside rel/href.",
          "is_bot": false,
          "headline": "fix(web): emit links[].type attribute in renderHead",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T15:47:37Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "cc4d66b503a1b5dc285961c823b14825409f96c3",
          "body": "Add a core-concepts page with a live demo, reorder the sidebar by\nlearning priority, drop the redundant Introduction next steps list, and\ncross-link from the API core and Portal guides.",
          "is_bot": false,
          "headline": "docs(website): add Error boundaries guide and tidy intro nav",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T15:05:08Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "a2092debfa74cca682df64812e57332374dc108c",
          "body": "Release/2026 07 08",
          "is_bot": false,
          "headline": "Merge pull request #32 from Open-Tech-Foundation/release/2026-07-08",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T11:11:52Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "c508a278a0cd5def62602f074812dc6632ff5bb5",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/create-web@0.16.0, @opentf/web-compiler@0.9.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T11:11:07Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "455f4fea99ab323d3b2a2199bd30d99e6adf148e",
          "body": "…ixes",
          "is_bot": false,
          "headline": "docs(web-compiler): changelog entries for the JSX-in-callback scope f…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T11:10:39Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "e6b1992205541267a6841ac55e9ffb20e99c97fd",
          "body": null,
          "is_bot": false,
          "headline": "chore(create-web): note optional blog prompt in changelog",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T11:08:52Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "88385cdd33fd4ff9d2bf6d0b92162a609776d46d",
          "body": "Ask developers whether to include a sample blog when scaffolding a docs\nsite. When enabled, add app/blog/, the blog config block, a Blog navbar\nlink, and intro copy; when disabled, ship docs only.\n\nLabel the website /blog route as a web-docs feature demo and expand the\ndocs introduction fullstack bullet list.",
          "is_bot": false,
          "headline": "feat(create-web): optional blog prompt for docs scaffold",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T11:08:30Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "aa41220a45b37ff010d459eed85b3f10625b4683",
          "body": "Same hole as $effect, same fix: onMount/onCleanup/onResize/\nonVisibilityChange/onMediaQuery callbacks and the $expose object were\nonly .value-injected, never probed for JSX, so an embedded\n<Child item={item}/> leaked verbatim into the emitted module.\n\nAll callback-taking macros now share the $effect\n[…]\nceholders,\ncapturing the callback's locals. dom_hook_closures moved onto the\nEmitter so the callbacks' helper usage feeds the module's import set\n(hydrate keeps a free wrapper, dom_hook_closures_pub).",
          "is_bot": false,
          "headline": "fix(compiler): template JSX in $expose and lifecycle hook callbacks",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T10:55:59Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "720a4f26f764ca74e8fa4d2d0c99b9863fc3c553",
          "body": "…uide\n\nMove provider-specific Workers setup under a platform examples section and\nupdate cross-links so deployment docs stay hosting-agnostic.",
          "is_bot": false,
          "headline": "docs: replace Cloudflare deployment page with generic Fetch handler g…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T10:51:49Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "d0c7de9bb41b8753bcd8c6526c016eb450122699",
          "body": "Use the OTF SVG for the navbar logo and favicon, and replace the footer\nwith a left-aligned Open Tech Foundation link to opentechf.org.",
          "is_bot": false,
          "headline": "feat(website): update branding with OTF logo in nav and footer",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T10:33:00Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "779486e5509706a0b01e60aff9839f982c4be3e3",
          "body": "Replace the single-command InstallPill with InstallTabs so visitors can\nswitch between npm, pnpm, and bun scaffold commands and copy the active one.",
          "is_bot": false,
          "headline": "feat(website): add package-manager chips to hero install command",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T10:23:11Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "5d8febe5dbb998e1deea9d6d2b0166cafc7989ad",
          "body": "A $effect body containing JSX (the reported shape: a plain for loop\npushing <Child group={group}/> into an array, then replaceChildren)\nwas injected verbatim — effect arguments were never probed for JSX,\nso raw JSX leaked into the emitted module.\n\nEffect args are now templated in lowering (Lowered.e\n[…]\nloop/callback locals\nare captured in exactly the scope the JSX was written in. Hydrate\nreuses the CSR emission via csr::effect_code_pub (effects always\nbuild fresh nodes; SSG drops effects as before).",
          "is_bot": false,
          "headline": "fix(compiler): template JSX embedded in $effect callbacks",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T10:21:42Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "11c720c7b41463817ff26dbf58de29ccad37e38c",
          "body": "Add a core-concepts JSX page covering supported patterns, pitfalls, and\nsix interactive examples. Wire it into the docs nav and add demo styles.",
          "is_bot": false,
          "headline": "docs(website): add JSX reference guide with live demos",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T10:16:17Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "13bed834eafdc805005b2b0a5e472df9483b0b27",
          "body": "A JSX value embedded in a preserved statement (groups.push(<Child\ngroup={group}/>) inside a for body), a JSX-valued prop, or a list-source\nexpression compiled to a node-builder hoisted to the component body while\nits effects and handlers referenced the enclosing scope's locals —\nthrowing ReferenceEr\n[…]\n now\nsubstitutes each branch inline as an IIFE at its placeholder, so the\nbuilt view evaluates in the scope the JSX was written in. SSG already\ninlined; hydrate still rejects JSX-as-value (Phase 2.1).",
          "is_bot": false,
          "headline": "fix(compiler): capture loop/callback locals in JSX-as-value builders",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T07:45:52Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "a321e78256690e325bf5ebd71c8877cb06453356",
          "body": "Replace the bare App template with spa (browser-only) and fullstack\n(middleware, loader, API route, otfw serve). Clarify scaffolder prompts\nand installation docs for developers new to SPA vs fullstack. Bump\ntemplate dependency floors to current @opentf releases.",
          "is_bot": false,
          "headline": "feat(create-web): split SPA and Fullstack templates (@0.15.0)",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T07:35:07Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "0548d9a7cb571e29e4896fdf70c5eca8f9dcfc96",
          "body": "Document first-paint DOM adoption for SSG and SSR, SPA navigation\nafter hydrate, mismatch recovery, and what constructs adopt today.\nLink from static generation, server, intro, portal, and data fetching.",
          "is_bot": false,
          "headline": "docs(website): add Hydration guide under deployment",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T07:20:25Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "bb4cbfa2e31c22dcc5a901c9f649531e8d961cc1",
          "body": "Introduce /docs/core-concepts/portal focused on relocation and the\nnative dialog alternative. Link from Context and API core without\nduplicating the context guide's theme demo.",
          "is_bot": false,
          "headline": "docs(website): add Portal guide with clip-escape demo",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T07:20:25Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "5ffdd39f7da47442c2d5466ed7a09df6e555f2cf",
          "body": "chore(release): @opentf/web@0.17.0",
          "is_bot": false,
          "headline": "Merge pull request #31 from Open-Tech-Foundation/release/2026-07-08",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T06:37:37Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "37ac44986b001e3d7c7108fb529f8e4c2a070228",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web@0.17.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T06:37:15Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "16efc37963f6f0a833142313c379d95be68e661d",
          "body": null,
          "is_bot": false,
          "headline": "docs(web): changelog for stale-chunk reload recovery",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T06:36:12Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "15c9a5874af0566674c44a2660080fe7b6ccaddd",
          "body": "Introduce /docs/routing/cookies with read/write examples for middleware,\nAPI routes, and loaders, and link to it from related docs instead of\nduplicating cookie content inline.",
          "is_bot": false,
          "headline": "docs(website): add standalone Cookies guide under routing",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T06:32:44Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "2b5b8bb63d13c7f49c9ee0cc7246f5b07b42fd61",
          "body": "…ploy\n\nA code-split route's lazy import() fails when its content-hashed chunk was removed by\na redeploy: a tab still running the old index.html holds the old chunk names, so the\nnext navigation to a not-yet-loaded route 404s (\"Failed to fetch dynamically imported\nmodule\"). On that failure the router\n[…]\naces the error instead of looping.\n\nNo HEAD probe to classify the failure first — it isn't reliable across hosts (405 /\nno-HEAD support, S3 returning 403 for missing keys, CORS preflight, CDN quirks).",
          "is_bot": false,
          "headline": "fix(web): reload once to recover from stale route chunks after a rede…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-08T06:30:26Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "204c5a44bc09ca0f9ee3e0085f48c4ffeca1dd92",
          "body": "Align website package.json with @opentf/web@0.16.0, web-docs@0.12.0,\nweb-form@1.11.0, web-i18n@1.11.0, and web-cli@1.12.0 so standalone\ninstalls and the lockfile match current published versions.",
          "is_bot": false,
          "headline": "chore(website): bump @opentf dependencies to latest releases",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T22:17:05Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "b6320cb80ea2f688e4f0a423a915d81a0e2a350f",
          "body": "Add Server API cookies reference, update middleware and deployment guides,\nlist cookie helpers on the home page, add the Server card to the API index,\nand align the docs version badge with @opentf/web@0.16.0.",
          "is_bot": false,
          "headline": "docs(website): document cookie helpers and bump docs to v0.16.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T22:02:59Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "2aab39a3c1fcd876a53abd8c09806865027bd1ce",
          "body": "chore(release): @opentf/web-cli@1.12.0, @opentf/web@0.16.0",
          "is_bot": false,
          "headline": "Merge pull request #30 from Open-Tech-Foundation/release/2026-07-07",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:56:08Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "16138f998495b67ceddf8ce17f885c957f1ab7f3",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.12.0, @opentf/web@0.16.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:55:10Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "548b182ba4b92a8e9d2e2e23d13bfe6388d5adcc",
          "body": "…ie/serializeCookie\n\nStandards-based Cookie / Set-Cookie wrappers in @opentf/web/server for\nmiddleware, API handlers, and loaders, closing the ergonomics gap with\nNext.js's request.cookies. Reads accept a Request, Headers, or raw header\nstring (percent-decoded, quoted form tolerated, first duplicate\n[…]\nrd now uses getCookie, the root middleware setCookies every response,\nand serve e2e asserts the Set-Cookie header survives to the client.\ndocs/MIDDLEWARE.md gains §3 Cookies; examples use the helpers.",
          "is_bot": false,
          "headline": "feat(web): cookie helpers — getCookie/getCookies/setCookie/deleteCook…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:54:18Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "4d7fb08a22788e7373e4f4f442bda993f825a3a3",
          "body": "…ly framing\n\nUse Middleware across docs and homepage, rename Server nav pages, remove the\nduplicate middleware section from deployment/server, and clarify pipeline\nmiddleware vs app/api/_middleware.js-only apiHandler exports.",
          "is_bot": false,
          "headline": "docs(website): rename Request middleware to Middleware and fix API-on…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:47:09Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "6115910de76f1cacaaed3d180b4f4d765a91346e",
          "body": null,
          "is_bot": false,
          "headline": "chore: add AGENTS.md with git commit/push permission rule",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:39:35Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "0f2b6e560833c2106816d3d8192d8489eec64318",
          "body": "…ent guides\n\nAdd a dedicated Request Middleware guide, update Server API and Cloudflare\ndeploy docs to use apiRoutes + pipeline middleware, and cross-link from\nroute guards, project structure, data fetching, and the homepage capabilities.",
          "is_bot": false,
          "headline": "docs(website): document request middleware across routing and deploym…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:37:18Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "befa466abe1f8c2bcd4ce64bdbd2e73217696a3e",
          "body": "chore(release): @opentf/web-cli@1.11.0, @opentf/web@0.15.0",
          "is_bot": false,
          "headline": "Merge pull request #29 from Open-Tech-Foundation/release/2026-07-07",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:24:49Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "d1bd93280d844ae4a3b9b0ddfae618fc9a2edcb6",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.11.0, @opentf/web@0.15.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:24:20Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "90b903aadd511965b413bc3de8434fa0a5ccde86",
          "body": "…d loader data\n\n_middleware.{js,ts} files are no longer API-only: the new createMiddleware\nrunner wraps the entire request pipeline under otfw dev/serve and\ncreateFetchHandler, so app/_middleware.js gates SSR pages, API endpoints,\n__data.json loader requests, and 404s equally (the server-side counte\n[…]\nverned scopes instead of serving them unguarded.\n\nCovered by 16 new runner unit tests, locals threading tests, and 17 new\nserve e2e assertions; SPEC §11.5/§8.6 reconciled and docs/MIDDLEWARE.md\nadded.",
          "is_bot": false,
          "headline": "feat(web): request middleware for the whole pipeline — pages, API, an…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T21:18:16Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e6b84267badd4fdbe7b10657939706574891f9fe",
          "body": "chore(release): @opentf/web-cli@1.10.0, @opentf/web-compiler@0.8.0",
          "is_bot": false,
          "headline": "Merge pull request #28 from Open-Tech-Foundation/release/2026-07-07",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T20:42:08Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "ca3ab98c18733c80f3c13eaecdbb1111be2cdca7",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.10.0, @opentf/web-compiler@0.8.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T20:41:48Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "7a398fc277a506ba9b48db80d857105bd584ec8c",
          "body": "…-decode\n\nfetch already decompresses the upstream body, so relaying the upstream's\nContent-Encoding/Content-Length made the browser decode the plain body a\nsecond time (ERR_CONTENT_DECODING_FAILED). Also anchor the base-url\nbuild-gate test's cli.js path to the test file so it passes from any cwd.",
          "is_bot": false,
          "headline": "fix(web-cli): strip encoding headers in dev proxy to stop gzip double…",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T20:41:08Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "767f310d2b082efe6782691052d2082dff9c251c",
          "body": "Record the two compiler list-lowering fixes (key={index} binding and JSX\nin a list's data expression) in otfw_compiler and @opentf/web-compiler.",
          "is_bot": false,
          "headline": "docs(changelog): record list key-index and data-position JSX fixes",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T20:31:20Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "65b0d63f442b6d0609dbe047bbc153e6af4af768",
          "body": "Two list-lowering bugs in `array.map(...)` regions, fixed across all\nbackends (CSR, hydrate, SSG):\n\n1. `key={index}`: the key function bound a synthetic `_index` param but\n   the interned key expression referenced the callback's real index name,\n   so `key={idx}` read an undefined binding. The key f\n[…]\nhydrate) or an `{ __html }` marker (SSG). `ViewNode::List` gains a\n   `source_branches` field carrying those sub-trees. Previously only a\n   hoisted `const` worked; inline data now compiles correctly.",
          "is_bot": false,
          "headline": "fix(compiler): correct list key index param and JSX in list-source data",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T20:29:27Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "87f9292f246249b81e9483362ee2179681e504b7",
          "body": "chore(release): @opentf/web-cli@1.9.0, @opentf/web@0.14.0",
          "is_bot": false,
          "headline": "Merge pull request #27 from Open-Tech-Foundation/release/2026-07-07",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T19:26:13Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "358737204ec8d7764327cdeabd4f737e377cd850",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-cli@1.9.0, @opentf/web@0.14.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T19:25:46Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "74ec1427e5a3c9e03ccdac38750c3a8d161a7f33",
          "body": "otfw.config.js authored via defineDocsConfig now gets editor autocomplete and\ntype-checking for the dev proxy field (prefix -> target origin string, or\n{ target }). New ProxyConfig JSDoc typedef; validated in isolation (valid string/\nobject forms pass, a non-string/object value is rejected TS2322).",
          "is_bot": false,
          "headline": "types(web-docs): add proxy to the defineDocsConfig SiteConfig typedef",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T19:23:10Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "ea33eb2ccf6fba0fcbe308807962bc53d551d4c1",
          "body": "…(@opentf/web-cli)",
          "is_bot": false,
          "headline": "docs(changelog): record env/ctx bindings (@opentf/web) and dev proxy …",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T19:18:11Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "1028588ec750bd73b558931fd843accd98bf6da8",
          "body": "Team develops the website via `cd website && bun run dev|build`, so the root\nwebsite wrappers are gone:\n- Removed `build:web` (packages/web has no build script — it was broken),\n  `website:build` (depended on it), and `website:dev` (redundant).\n- Repointed `preview`/`deploy` at the working `cf:build` standalone build\n  instead of the removed `website:build`.\n- Added `typecheck` (`tsc --noEmit`).",
          "is_bot": false,
          "headline": "chore: clean up root scripts",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T19:17:45Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "626d778daee6e42a5f79851b4b89315a0a9249d0",
          "body": "- api.d.ts: the `app/**/route` JSDoc contained `*/`, prematurely closing the\n  comment and breaking the declaration parse (cascade of TS1003/1005/1443).\n- tsconfig: drop deprecated `baseUrl` (paths are already ./-relative; TS7 removes\n  it) and add `exclude` so build artifacts (dist, .dev, target, benchmark bundles)\n  aren't type-checked. tsc now exits 0.",
          "is_bot": false,
          "headline": "fix(ts): make `tsc --noEmit` clean",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T19:17:21Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "e0acb539a444b587af033527a1b59ca3ee6f7f57",
          "body": "…proxy)\n\nNew deployment/cloudflare page walks the end-to-end setup: worker.js entry\n(apiHandler + env.ASSETS fallback), wrangler.jsonc (assets binding + SPA\nfallback + d1_databases), reading D1 via context.env in handlers, and the dev\nstory — wrangler dev + otfw.config proxy so /api/* runs against a\n[…]\n context.env/ctx bindings and the fallback env-forwarding across\nthe server/API reference pages (docs/API.md, api/server, deployment/server) and\nthe new dev-only proxy config key (configuration page).",
          "is_bot": false,
          "headline": "docs: Cloudflare Workers full-stack deployment guide (SPA + D1 + dev …",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T18:41:42Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "1b34bab2bf2daa5746604000e60b13e3734e06a1",
          "body": "otfw dev can now forward configured path prefixes to a separately-running\nbackend instead of handling them in-process:\n\n  export default { proxy: { \"/api\": \"http://localhost:8787\" } };\n\nThis is the dev half of deploying to bindings-backed runtimes: run the API on\nthe real runtime (e.g. `wrangler dev\n[…]\nps serving the SPA + HMR. The proxy is checked\nbefore the in-process API handler, so proxied endpoints never double-run.\nPath/query/method/headers/body are preserved; an unreachable upstream is a 502.",
          "is_bot": false,
          "headline": "feat(cli): dev proxy for provider-agnostic backends (otfw.config proxy)",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T18:37:49Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "876f9170d800716138919800c16bd584ea7812d2",
          "body": "API handlers now receive the platform fetch arguments via context: on\nCloudflare Workers context.env holds the bindings (D1, KV, secrets) and\ncontext.ctx the execution context (waitUntil). createFetchHandler forwards\nenv/ctx to the handler and the fallback, so a static-asset fallback can call\nenv.ASSETS.fetch(request). Bun/Node leave them undefined (use process.env).",
          "is_bot": false,
          "headline": "feat(web): thread runtime env/ctx (Workers bindings) into API context",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T18:35:43Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "89b05f24b78452b20deeb5df8a37f3ed50b6234c",
          "body": "A dynamic hole holding an array — JSX (`{[<a/>, <b/>]}`) or primitives\n(`{[1, 2, 3]}`) — fell through `ssgText` to `String(v)`, emitting\n`[object Object],[object Object]` (or comma-joined text) into the SSG /\npre-rendered HTML. Dev/CSR rendered correctly (toNodes/bindText flatten\narrays) and the cli\n[…]\nparator,\nmirroring CSR's toNodes/bindText so the server HTML matches the hydrated\nrender. Adds a ssgText describe block covering JSX arrays, primitive\narrays, nesting, and the {__html}/escaping paths.",
          "is_bot": false,
          "headline": "fix(web): render array-valued dynamic holes instead of [object Object]",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T14:44:37Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "05095c88c785527b20691c4773aa2dcec02ca25a",
          "body": "chore(release): @opentf/web-compiler@0.7.0",
          "is_bot": false,
          "headline": "Merge pull request #26 from Open-Tech-Foundation/release/2026-07-07",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T12:37:21Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "9ad24f5c412dc7d7b4dd1ec51aa56bb89c907df5",
          "body": null,
          "is_bot": false,
          "headline": "chore(release): @opentf/web-compiler@0.7.0",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T12:36:53Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "69db69d59fd1bd98eb5c903bda41230f4ba1d64b",
          "body": "Populate the [Unreleased] sections the release preflight flagged as empty for\nthe packages with commits since their last tag — all test-only changes:\n\n- web: hi-fi runtime tests moved to real Chromium; hydration construct matrix.\n- web-cli: real-browser runtime orchestrator; Portal-across-hydration \n[…]\nl-until-condition waits replacing fixed settle sleeps.\n- web-docs: mobile-drawer e2e polls the transition end-state instead of sleeping.\n- web-test: browser-runner.js bun:test-compatible in-page shim.",
          "is_bot": false,
          "headline": "docs(changelog): record test-tier work under [Unreleased]",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T12:33:22Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e4f45c20a1970d618dd33d75db552c9508401af0",
          "body": "A valueless prop on a component (`<Toggle disabled/>`) was lowered to an\nempty-string static, so the component read the falsy `\"\"` instead of the\n`true` that JSX semantics (React/Solid/Preact) imply. It now crosses as the\nJS boolean `true` across all backends: CSR `setProp(el, \"disabled\", true)`,\nSS\n[…]\nnts are unchanged — a valueless attribute (`<input disabled/>`)\nstays the empty-string presence attribute, which is HTML-correct.\n\nAdds a `PropValue::Boolean` IR variant, produced only for components.",
          "is_bot": false,
          "headline": "fix(compiler): pass valueless boolean props to components as true",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T12:18:21Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "29c2de7418d06b6e5e27c1374f18022c0d7897bf",
          "body": "Homepage adds Partial status pill; dev server capability reflects\nfull-page refresh on save. CLI and getting-started docs clarify what\nreloads automatically vs what needs a restart; module HMR stays planned.",
          "is_bot": false,
          "headline": "docs(website): label dev reload as partial, not module HMR",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T11:52:42Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "40c91ff61950253967ae743e5d702cddd5e73dff",
          "body": "The browser e2e suites paced themselves with fixed `sleep()`s after each action\n(hydrate settle, click, viewport change, drawer open/close animation, SPA nav),\nwhich flake on a slow CI runner — too short and the assertion races the effect.\n\nReplaces each with a condition-wait that polls the exact en\n[…]\ns\n  open/close transition end-state and the desktop media-query layout.\n\nOnly the `fetchJSON` readiness poll and the waiters' own poll interval remain as\nsleeps. Ran each suite repeatedly — all green.",
          "is_bot": false,
          "headline": "test(e2e): replace fixed settle sleeps with poll-until-condition waits",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T11:52:09Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e423f1686edd4edd55d640651f320a871a95e3e7",
          "body": "The browser e2e suites (serve, build-data, hydrate-browser, lifecycle-hooks,\nruntime-browser, and web-docs mobile-drawer) drive `otfw serve`/`build` + headless\nChrome over CDP and were never gated in CI — they skip cleanly without a browser,\nso the fidelity tier (custom-element upgrade timing, porta\n[…]\nges' browser suites with CHROME_BIN set. Prints\n`chrome --version` first so a bad binary path fails loudly instead of silently\nskipping to a false green. Runs in parallel with the fast `bun test` job.",
          "is_bot": false,
          "headline": "ci: run the real-browser e2e tier in a dedicated job",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T11:32:13Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "b784c05539c76edbf2fc8217660887994f33c7cf",
          "body": "Add both as supported Core features; mention $context in the reactive\nmacros line.",
          "is_bot": false,
          "headline": "docs(website): list Context API and Portal on homepage capabilities",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T09:03:07Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "3529e158fa00e3a510e64180b26789f04fd39ccc",
          "body": "Document which conditional patterns update with signals (inline JSX\nholes, root JSX ternaries) vs freeze at first connect (early returns,\ncached JSX locals, guard return paths).",
          "is_bot": false,
          "headline": "docs(website): explain init-once vs reactive conditionals in templating",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T08:58:02Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "7ad3b53e535dd8027c601965805d1cebaad4a406",
          "body": "Document module-scoped tags (web-badge-<hash>), the stable web-badge\nclass hook for CSS, and when to use raw custom elements vs JSX.",
          "is_bot": false,
          "headline": "docs(website): fix component registry tag and native interop",
          "author_name": "Thanga Ganapathy",
          "author_login": "Thanga-Ganapathy",
          "committed_at": "2026-07-07T08:54:51Z",
          "body_truncated": false,
          "is_coding_agent": false
        }
      ],
      "releases_count": 100,
      "commits_last_year": 596,
      "latest_release_at": "2026-07-19T06:20:27Z",
      "latest_release_tag": "@opentf/web-cli@1.18.0",
      "releases_from_tags": false,
      "days_since_last_push": 4,
      "active_weeks_last_year": 9,
      "days_since_latest_release": 4,
      "mean_days_between_releases": 0.1
    },
    "community": {
      "has_readme": true,
      "has_license": true,
      "has_description": true,
      "has_contributing": false,
      "health_percentage": 37,
      "has_issue_template": false,
      "has_code_of_conduct": false,
      "has_pull_request_template": false
    },
    "ecosystem": {
      "packages": [
        {
          "name": "@opentf/web",
          "exists": true,
          "license": "MIT",
          "keywords": [
            "opentf",
            "web-components",
            "signals",
            "reactivity",
            "runtime",
            "ssg"
          ],
          "ecosystem": "npm",
          "matches_repo": true,
          "registry_url": "https://www.npmjs.com/package/@opentf/web",
          "is_deprecated": false,
          "latest_version": "0.20.0",
          "repository_url": "https://github.com/Open-Tech-Foundation/Web-App-Framework",
          "versions_count": 20,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": 1,
          "monthly_downloads": 3607,
          "first_published_at": "2026-04-23T11:51:27.912000Z",
          "latest_published_at": "2026-07-18T14:12:35.564000Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 5
        },
        {
          "name": "@opentf/web-cli",
          "exists": true,
          "license": "MIT",
          "keywords": [
            "opentf",
            "web",
            "dev-server",
            "ssg",
            "rolldown",
            "toolchain"
          ],
          "ecosystem": "npm",
          "matches_repo": true,
          "registry_url": "https://www.npmjs.com/package/@opentf/web-cli",
          "is_deprecated": false,
          "latest_version": "1.18.0",
          "repository_url": "https://github.com/Open-Tech-Foundation/Web-App-Framework",
          "versions_count": 22,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": 1,
          "monthly_downloads": 3495,
          "first_published_at": "2026-06-21T21:27:30.705000Z",
          "latest_published_at": "2026-07-19T06:20:24.650000Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 4
        },
        {
          "name": "@opentf/web-docs",
          "exists": true,
          "license": "MIT",
          "keywords": [
            "opentf",
            "documentation",
            "docs",
            "mdx",
            "static-site-generator",
            "ssg"
          ],
          "ecosystem": "npm",
          "matches_repo": true,
          "registry_url": "https://www.npmjs.com/package/@opentf/web-docs",
          "is_deprecated": false,
          "latest_version": "0.17.0",
          "repository_url": "https://github.com/Open-Tech-Foundation/Web-App-Framework",
          "versions_count": 17,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": 1,
          "monthly_downloads": 3015,
          "first_published_at": "2026-06-22T11:54:22.552000Z",
          "latest_published_at": "2026-07-18T14:12:47.159000Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 5
        },
        {
          "name": "@opentf/web-form",
          "exists": true,
          "license": null,
          "keywords": [],
          "ecosystem": "npm",
          "matches_repo": null,
          "registry_url": "https://www.npmjs.com/package/@opentf/web-form",
          "is_deprecated": false,
          "latest_version": "1.15.0",
          "repository_url": null,
          "versions_count": 18,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": 1,
          "monthly_downloads": 2581,
          "first_published_at": "2026-04-23T11:51:28.492000Z",
          "latest_published_at": "2026-07-18T14:12:50.918000Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 5
        },
        {
          "name": "@opentf/web-i18n",
          "exists": true,
          "license": null,
          "keywords": [
            "opentf",
            "i18n",
            "internationalization",
            "icu",
            "intl",
            "localization"
          ],
          "ecosystem": "npm",
          "matches_repo": null,
          "registry_url": "https://www.npmjs.com/package/@opentf/web-i18n",
          "is_deprecated": false,
          "latest_version": "1.15.0",
          "repository_url": null,
          "versions_count": 15,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": 1,
          "monthly_downloads": 2563,
          "first_published_at": "2026-07-02T07:40:14.249000Z",
          "latest_published_at": "2026-07-18T14:12:54.711000Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 5
        },
        {
          "name": "@opentf/web-test",
          "exists": true,
          "license": null,
          "keywords": [],
          "ecosystem": "npm",
          "matches_repo": null,
          "registry_url": "https://www.npmjs.com/package/@opentf/web-test",
          "is_deprecated": false,
          "latest_version": "1.15.0",
          "repository_url": null,
          "versions_count": 16,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": 1,
          "monthly_downloads": 2481,
          "first_published_at": "2026-06-21T21:27:30.613000Z",
          "latest_published_at": "2026-07-18T14:12:39.417000Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 5
        }
      ]
    },
    "popularity": {
      "forks": 0,
      "stars": 0,
      "watchers": 0,
      "fork_history": {
        "days": [],
        "complete": true,
        "collected": 0,
        "total_forks": 0
      },
      "star_history": {
        "days": [],
        "complete": true,
        "collected": 0,
        "total_stars": 0,
        "collected_at": null
      },
      "open_issues_and_prs": 0
    },
    "ai_readiness": {
      "has_nix": false,
      "example_dirs": [],
      "has_llms_txt": false,
      "has_dockerfile": false,
      "has_mcp_signal": false,
      "bootstrap_files": [],
      "api_schema_files": [],
      "has_devcontainer": false,
      "typecheck_configs": [
        "packages/create-web/templates/docs/jsconfig.json",
        "packages/create-web/templates/fullstack/jsconfig.json",
        "packages/create-web/templates/library/jsconfig.json",
        "packages/create-web/templates/spa/jsconfig.json",
        "tsconfig.json"
      ],
      "toolchain_manifests": [
        "Cargo.toml",
        "crates/otfw_cli/Cargo.toml",
        "crates/otfw_compiler/Cargo.toml",
        "crates/otfw_ir/Cargo.toml"
      ],
      "largest_source_bytes": 139665,
      "source_files_sampled": 326,
      "oversized_source_files": 3,
      "agent_instruction_files": [
        "AGENTS.md"
      ],
      "agent_instruction_max_bytes": 274
    },
    "dependencies": {
      "manifests": [
        "Cargo.toml",
        "package.json",
        "playground/package.json",
        "website/package.json"
      ],
      "advisories": {
        "error": null,
        "scope": null,
        "source": null,
        "findings": [],
        "collected": false,
        "malicious": [],
        "truncated": false,
        "by_severity": {},
        "advisory_count": 0,
        "affected_count": 0,
        "assessed_count": 0,
        "malicious_count": 0,
        "assessed_package": null,
        "unassessed_count": 0,
        "direct_affected_count": 0
      },
      "ecosystems": [
        "crates",
        "npm"
      ],
      "dependencies": [
        {
          "name": "@opentf/web",
          "manifest": "playground/package.json",
          "ecosystem": "npm",
          "version_constraint": "workspace:*"
        },
        {
          "name": "@opentf/web-form",
          "manifest": "playground/package.json",
          "ecosystem": "npm",
          "version_constraint": "workspace:*"
        },
        {
          "name": "monaco-editor",
          "manifest": "playground/package.json",
          "ecosystem": "npm",
          "version_constraint": "^0.52.2"
        },
        {
          "name": "@monaco-editor/loader",
          "manifest": "playground/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.4.0"
        },
        {
          "name": "prismjs",
          "manifest": "playground/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.29.0"
        },
        {
          "name": "zod",
          "manifest": "playground/package.json",
          "ecosystem": "npm",
          "version_constraint": "^4.3.6"
        },
        {
          "name": "@opentf/web",
          "manifest": "website/package.json",
          "ecosystem": "npm",
          "version_constraint": "^0.20.0"
        },
        {
          "name": "@opentf/web-docs",
          "manifest": "website/package.json",
          "ecosystem": "npm",
          "version_constraint": "^0.17.0"
        },
        {
          "name": "@opentf/web-form",
          "manifest": "website/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.15.0"
        },
        {
          "name": "@opentf/web-i18n",
          "manifest": "website/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.15.0"
        },
        {
          "name": "otfw_compiler",
          "manifest": "crates/otfw_cli/Cargo.toml",
          "ecosystem": "crates",
          "version_constraint": null
        },
        {
          "name": "markdown",
          "manifest": "crates/otfw_compiler/Cargo.toml",
          "ecosystem": "crates",
          "version_constraint": "1.0.0"
        },
        {
          "name": "otfw_ir",
          "manifest": "crates/otfw_compiler/Cargo.toml",
          "ecosystem": "crates",
          "version_constraint": null
        },
        {
          "name": "oxc",
          "manifest": "crates/otfw_compiler/Cargo.toml",
          "ecosystem": "crates",
          "version_constraint": null
        },
        {
          "name": "syntect",
          "manifest": "crates/otfw_compiler/Cargo.toml",
          "ecosystem": "crates",
          "version_constraint": "5"
        },
        {
          "name": "kolorist",
          "manifest": "packages/create-web/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.8.0"
        },
        {
          "name": "prompts",
          "manifest": "packages/create-web/package.json",
          "ecosystem": "npm",
          "version_constraint": "^2.4.2"
        },
        {
          "name": "@opentf/web-compiler",
          "manifest": "packages/web-cli/package.json",
          "ecosystem": "npm",
          "version_constraint": "0.10.0"
        },
        {
          "name": "@tailwindcss/node",
          "manifest": "packages/web-cli/package.json",
          "ecosystem": "npm",
          "version_constraint": "4.2.2"
        },
        {
          "name": "@tailwindcss/oxide",
          "manifest": "packages/web-cli/package.json",
          "ecosystem": "npm",
          "version_constraint": "4.2.2"
        },
        {
          "name": "rolldown",
          "manifest": "packages/web-cli/package.json",
          "ecosystem": "npm",
          "version_constraint": "1.0.0-rc.17"
        },
        {
          "name": "tailwindcss",
          "manifest": "packages/web-cli/package.json",
          "ecosystem": "npm",
          "version_constraint": "4.2.2"
        },
        {
          "name": "pagefind",
          "manifest": "packages/web-docs/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.5.2"
        },
        {
          "name": "@opentf/std",
          "manifest": "packages/web-form/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.0.0-beta.2"
        },
        {
          "name": "intl-messageformat",
          "manifest": "packages/web-i18n/package.json",
          "ecosystem": "npm",
          "version_constraint": "^10.7.0"
        },
        {
          "name": "@testing-library/dom",
          "manifest": "packages/web-test/package.json",
          "ecosystem": "npm",
          "version_constraint": "^10.4.1"
        },
        {
          "name": "@testing-library/user-event",
          "manifest": "packages/web-test/package.json",
          "ecosystem": "npm",
          "version_constraint": "^14.6.1"
        },
        {
          "name": "happy-dom",
          "manifest": "packages/web-test/package.json",
          "ecosystem": "npm",
          "version_constraint": "^20.9.0"
        }
      ],
      "all_dependencies": {
        "error": "GitHub dependency-graph SBOM unavailable (404); the dependency graph may be disabled for this repository",
        "source": null,
        "packages": [],
        "collected": false,
        "truncated": false,
        "total_count": null,
        "direct_count": null,
        "indirect_count": null
      }
    },
    "maintainership": {
      "issues": {
        "open_prs": 0,
        "merged_prs": 37,
        "open_issues": 0,
        "closed_ratio": null,
        "closed_issues": 0,
        "closed_unmerged_prs": 1
      },
      "bus_factor": 1,
      "bot_contributors": 1,
      "top_contributors": [
        {
          "type": "User",
          "login": "Thanga-Ganapathy",
          "commits": 587,
          "avatar_url": "https://avatars.githubusercontent.com/u/22178434?v=4"
        }
      ],
      "contributors_sampled": 1,
      "top_contributor_share": 1
    },
    "quality_signals": {
      "has_ci": true,
      "has_tests": true,
      "ci_workflows": [
        "ci.yml",
        "release.yml"
      ],
      "has_docs_dir": true,
      "linter_configs": [],
      "has_editorconfig": false,
      "has_linter_config": false,
      "has_precommit_config": false
    },
    "security_signals": {
      "lockfiles": [
        "Cargo.lock"
      ],
      "scorecard": {
        "checks": [
          {
            "name": "Binary-Artifacts",
            "score": 8,
            "reason": "binaries present in source code",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#binary-artifacts"
          },
          {
            "name": "Branch-Protection",
            "score": 0,
            "reason": "branch protection not enabled on development/release branches",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#branch-protection"
          },
          {
            "name": "CI-Tests",
            "score": 8,
            "reason": "4 out of 5 merged PRs checked by a CI test -- score normalized to 8",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#ci-tests"
          },
          {
            "name": "CII-Best-Practices",
            "score": 0,
            "reason": "no effort to earn an OpenSSF best practices badge detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#cii-best-practices"
          },
          {
            "name": "Code-Review",
            "score": 0,
            "reason": "Found 0/25 approved changesets -- score normalized to 0",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#code-review"
          },
          {
            "name": "Contributors",
            "score": 0,
            "reason": "project has 0 contributing companies or organizations -- score normalized to 0",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#contributors"
          },
          {
            "name": "Dangerous-Workflow",
            "score": 10,
            "reason": "no dangerous workflow patterns detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#dangerous-workflow"
          },
          {
            "name": "Dependency-Update-Tool",
            "score": 0,
            "reason": "no update tool detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#dependency-update-tool"
          },
          {
            "name": "Fuzzing",
            "score": 0,
            "reason": "project is not fuzzed",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#fuzzing"
          },
          {
            "name": "License",
            "score": 10,
            "reason": "license file detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#license"
          },
          {
            "name": "Maintained",
            "score": 10,
            "reason": "30 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#maintained"
          },
          {
            "name": "Packaging",
            "score": null,
            "reason": "packaging workflow not detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#packaging"
          },
          {
            "name": "Pinned-Dependencies",
            "score": 0,
            "reason": "dependency not pinned by hash detected -- score normalized to 0",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#pinned-dependencies"
          },
          {
            "name": "SAST",
            "score": 0,
            "reason": "SAST tool is not run on all commits -- score normalized to 0",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#sast"
          },
          {
            "name": "Security-Policy",
            "score": 0,
            "reason": "security policy file not detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#security-policy"
          },
          {
            "name": "Signed-Releases",
            "score": null,
            "reason": "no releases found",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#signed-releases"
          },
          {
            "name": "Token-Permissions",
            "score": 0,
            "reason": "detected GitHub workflow tokens with excessive permissions",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#token-permissions"
          },
          {
            "name": "Vulnerabilities",
            "score": 0,
            "reason": "19 existing vulnerabilities detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#vulnerabilities"
          }
        ],
        "commit": "ec0b269b5901225e8c3dfbffaf9818fa47051734",
        "ran_at": "2026-07-23T21:57:04Z",
        "aggregate_score": 3,
        "scorecard_version": "v5.5.0"
      },
      "has_codeql_workflow": false,
      "has_security_policy": false,
      "has_dependabot_config": false
    },
    "contribution_flow": {
      "collected": true,
      "ci_last_run_at": "2026-07-19T06:20:45Z",
      "oldest_open_prs": [],
      "last_merged_pr_at": "2026-07-19T06:19:54Z",
      "ci_last_conclusion": "SUCCESS",
      "oldest_open_issues": []
    }
  },
  "config": {
    "disabled_metrics": [],
    "disabled_categories": [],
    "disabled_components": {}
  },
  "source": {
    "url": "https://github.com/Open-Tech-Foundation/Web-App-Framework",
    "host": "github.com",
    "name": "Web-App-Framework",
    "owner": "Open-Tech-Foundation"
  },
  "metrics": {
    "overall": {
      "key": "overall",
      "band": "moderate",
      "name": "Overall health",
      "note": null,
      "notes": [],
      "value": 57,
      "inputs": {
        "security": 30,
        "vitality": 82,
        "community": 36,
        "governance": 55,
        "engineering": 74
      },
      "components": []
    },
    "categories": [
      {
        "key": "vitality",
        "band": "good",
        "name": "Vitality",
        "value": 82,
        "weight": 0.22,
        "metrics": [
          {
            "key": "development_activity",
            "band": "good",
            "name": "Development activity",
            "note": null,
            "notes": [],
            "value": 70,
            "inputs": {
              "commits_last_year": 596,
              "human_commit_share": 1,
              "days_since_last_push": 4,
              "active_weeks_last_year": 9
            },
            "components": [
              {
                "key": "push_recency",
                "name": "Push recency",
                "detail": "last push 4 days ago",
                "points": 36,
                "status": "met",
                "details": [
                  {
                    "code": "push_recency",
                    "params": {
                      "days": 4
                    }
                  }
                ],
                "max_points": 36
              },
              {
                "key": "commit_cadence",
                "name": "Commit cadence",
                "detail": "9/52 weeks with commits",
                "points": 6.2,
                "status": "partial",
                "details": [
                  {
                    "code": "commit_cadence_weeks",
                    "params": {
                      "weeks": 9
                    }
                  }
                ],
                "max_points": 36
              },
              {
                "key": "commit_volume",
                "name": "Commit volume",
                "detail": "596 commits in the last year",
                "points": 18,
                "status": "met",
                "details": [
                  {
                    "code": "commits_last_year",
                    "params": {
                      "count": 596
                    }
                  }
                ],
                "max_points": 18
              },
              {
                "key": "openssf_scorecard_maintained",
                "name": "OpenSSF Scorecard: Maintained",
                "detail": "30 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10",
                "points": 10,
                "status": "met",
                "details": [],
                "max_points": 10
              }
            ]
          },
          {
            "key": "release_discipline",
            "band": "excellent",
            "name": "Release discipline",
            "note": "Excluded from scoring (no data or not applicable): OpenSSF Scorecard: Signed-Releases. Remaining weights renormalized.",
            "notes": [
              {
                "code": "excluded_no_data",
                "params": {
                  "components": [
                    "openssf_scorecard_signed_releases"
                  ]
                }
              },
              {
                "code": "weights_renormalized",
                "params": {}
              }
            ],
            "value": 100,
            "inputs": {
              "releases_count": 100,
              "latest_release_tag": "@opentf/web-cli@1.18.0",
              "releases_from_tags": false,
              "days_since_latest_release": 4,
              "mean_days_between_releases": 0.1
            },
            "components": [
              {
                "key": "ships_releases",
                "name": "Ships releases",
                "detail": "100 releases published",
                "points": 27,
                "status": "met",
                "details": [
                  {
                    "code": "releases_published",
                    "params": {
                      "count": 100
                    }
                  }
                ],
                "max_points": 27
              },
              {
                "key": "release_recency",
                "name": "Release recency",
                "detail": "latest release 4 days ago",
                "points": 36,
                "status": "met",
                "details": [
                  {
                    "code": "release_recency",
                    "params": {
                      "days": 4
                    }
                  }
                ],
                "max_points": 36
              },
              {
                "key": "release_cadence",
                "name": "Release cadence",
                "detail": "a release every ~0.1 days",
                "points": 27,
                "status": "met",
                "details": [
                  {
                    "code": "release_cadence",
                    "params": {
                      "gap": 0.1
                    }
                  }
                ],
                "max_points": 27
              },
              {
                "key": "openssf_scorecard_signed_releases",
                "name": "OpenSSF Scorecard: Signed-Releases",
                "detail": "no releases found",
                "points": 0,
                "status": "excluded",
                "details": [
                  {
                    "code": "no_data",
                    "params": {}
                  }
                ],
                "max_points": 10
              }
            ]
          },
          {
            "key": "abandonment",
            "band": "excellent",
            "name": "Abandonment",
            "note": null,
            "notes": [],
            "value": 100,
            "inputs": {
              "cap": null,
              "state": "unverified",
              "guards": [],
              "signals": [],
              "red_flag": false,
              "multiplier_pct": 100,
              "declared_reason": null,
              "unverified_reason": "repository_too_young",
              "unanswered_open_prs": null,
              "unanswered_open_issues": null,
              "days_since_last_merged_pr": null,
              "days_since_last_human_commit": null,
              "days_since_last_human_commit_is_floor": false
            },
            "components": [
              {
                "key": "project_is_still_maintained",
                "name": "Project is still maintained",
                "detail": "maintenance record not established from the collected data",
                "points": 100,
                "status": "met",
                "details": [
                  {
                    "code": "abandonment_unverified",
                    "params": {}
                  }
                ],
                "max_points": 100
              }
            ]
          }
        ],
        "description": "Is the project alive — is code being written and are releases shipping?"
      },
      {
        "key": "community",
        "band": "at_risk",
        "name": "Community & Adoption",
        "value": 36,
        "weight": 0.18,
        "metrics": [
          {
            "key": "popularity",
            "band": "critical",
            "name": "Popularity & adoption",
            "note": null,
            "notes": [],
            "value": 1,
            "inputs": {
              "forks": 0,
              "stars": 0,
              "watchers": 0,
              "growth_state": "unverified",
              "growth_factor_pct": 100,
              "growth_unverified_reason": "no_history"
            },
            "components": [
              {
                "key": "stars",
                "name": "Stars",
                "detail": "0 stars",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "stars",
                    "params": {
                      "count": 0
                    }
                  }
                ],
                "max_points": 60
              },
              {
                "key": "forks",
                "name": "Forks",
                "detail": "0 forks",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "forks",
                    "params": {
                      "count": 0
                    }
                  }
                ],
                "max_points": 25
              },
              {
                "key": "watchers",
                "name": "Watchers",
                "detail": "0 watchers",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "watchers",
                    "params": {
                      "count": 0
                    }
                  }
                ],
                "max_points": 15
              }
            ]
          },
          {
            "key": "community_health",
            "band": "moderate",
            "name": "Community health",
            "note": null,
            "notes": [],
            "value": 50,
            "inputs": {
              "has_readme": true,
              "has_license": true,
              "has_contributing": false,
              "has_issue_template": false,
              "has_code_of_conduct": false,
              "has_pull_request_template": false
            },
            "components": [
              {
                "key": "readme",
                "name": "README",
                "detail": null,
                "points": 22.5,
                "status": "met",
                "details": [],
                "max_points": 22.5
              },
              {
                "key": "license",
                "name": "License",
                "detail": "recognized license (MIT)",
                "points": 22.5,
                "status": "met",
                "details": [
                  {
                    "code": "license_standard",
                    "params": {}
                  },
                  {
                    "code": "license_spdx",
                    "params": {
                      "spdx": "MIT"
                    }
                  }
                ],
                "max_points": 22.5
              },
              {
                "key": "contributing_guide",
                "name": "CONTRIBUTING guide",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 18
              },
              {
                "key": "code_of_conduct",
                "name": "Code of conduct",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 13.5
              },
              {
                "key": "issue_template",
                "name": "Issue template",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.2
              },
              {
                "key": "pr_template",
                "name": "PR template",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 6.3
              }
            ]
          },
          {
            "key": "ecosystem_adoption",
            "band": "good",
            "name": "Ecosystem adoption (downloads)",
            "note": "Excluded from scoring (no data or not applicable): Registry dependents. Remaining weights renormalized.",
            "notes": [
              {
                "code": "excluded_no_data",
                "params": {
                  "components": [
                    "registry_dependents"
                  ]
                }
              },
              {
                "code": "weights_renormalized",
                "params": {}
              }
            ],
            "value": 71,
            "inputs": {
              "packages": [
                "@opentf/web",
                "@opentf/web-cli",
                "@opentf/web-docs",
                "@opentf/web-form",
                "@opentf/web-i18n",
                "@opentf/web-test"
              ],
              "dependents": null,
              "ecosystems": "npm",
              "total_downloads": null,
              "monthly_downloads": 17742
            },
            "components": [
              {
                "key": "monthly_downloads",
                "name": "Monthly downloads",
                "detail": "17,742 downloads/month across npm",
                "points": 56.7,
                "status": "partial",
                "details": [
                  {
                    "code": "downloads_monthly",
                    "params": {
                      "count": 17742,
                      "ecosystems": "npm"
                    }
                  }
                ],
                "max_points": 80
              },
              {
                "key": "registry_dependents",
                "name": "Registry dependents",
                "detail": "not reported by this ecosystem",
                "points": 0,
                "status": "excluded",
                "details": [
                  {
                    "code": "not_reported_by_this_ecosystem",
                    "params": {}
                  }
                ],
                "max_points": 20
              }
            ]
          }
        ],
        "description": "Does the project have users, downloads, attention, and a welcoming setup for contributors?"
      },
      {
        "key": "governance",
        "band": "moderate",
        "name": "Sustainability & Governance",
        "value": 55,
        "weight": 0.24,
        "metrics": [
          {
            "key": "maintainer_resilience",
            "band": "critical",
            "name": "Maintainer resilience (bus factor)",
            "note": null,
            "notes": [],
            "value": 10,
            "inputs": {
              "bus_factor": 1,
              "contributors_sampled": 1,
              "top_contributor_share": 1
            },
            "components": [
              {
                "key": "bus_factor",
                "name": "Bus factor",
                "detail": "1 contributor(s) cover half of all commits",
                "points": 9,
                "status": "partial",
                "details": [
                  {
                    "code": "bus_factor",
                    "params": {
                      "count": 1
                    }
                  }
                ],
                "max_points": 54
              },
              {
                "key": "commit_distribution",
                "name": "Commit distribution",
                "detail": "top contributor authored 100% of commits",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "top_contributor_share",
                    "params": {
                      "share": 100
                    }
                  }
                ],
                "max_points": 22.5
              },
              {
                "key": "contributor_breadth",
                "name": "Contributor breadth",
                "detail": "1 contributors",
                "points": 1.4,
                "status": "partial",
                "details": [
                  {
                    "code": "contributors_sampled",
                    "params": {
                      "count": 1
                    }
                  }
                ],
                "max_points": 13.5
              },
              {
                "key": "openssf_scorecard_contributors",
                "name": "OpenSSF Scorecard: Contributors",
                "detail": "project has 0 contributing companies or organizations -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 10
              }
            ]
          },
          {
            "key": "responsiveness",
            "band": "good",
            "name": "Issue & PR responsiveness",
            "note": "Excluded from scoring (no data or not applicable): Issue resolution. Remaining weights renormalized.",
            "notes": [
              {
                "code": "excluded_no_data",
                "params": {
                  "components": [
                    "issue_resolution"
                  ]
                }
              },
              {
                "code": "weights_renormalized",
                "params": {}
              }
            ],
            "value": 70,
            "inputs": {
              "merged_prs": 37,
              "open_issues": 0,
              "closed_issues": 0,
              "issue_closed_ratio": null,
              "closed_unmerged_prs": 1
            },
            "components": [
              {
                "key": "issue_resolution",
                "name": "Issue resolution",
                "detail": "no issues or no data",
                "points": 0,
                "status": "excluded",
                "details": [
                  {
                    "code": "no_issues_or_data",
                    "params": {}
                  }
                ],
                "max_points": 46.75
              },
              {
                "key": "pr_acceptance",
                "name": "PR acceptance",
                "detail": "37/38 decided PRs merged",
                "points": 37.2,
                "status": "partial",
                "details": [
                  {
                    "code": "decided_prs_merged",
                    "params": {
                      "merged": 37,
                      "decided": 38
                    }
                  }
                ],
                "max_points": 38.25
              },
              {
                "key": "openssf_scorecard_code_review",
                "name": "OpenSSF Scorecard: Code-Review",
                "detail": "Found 0/25 approved changesets -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 15
              }
            ]
          },
          {
            "key": "stewardship",
            "band": "moderate",
            "name": "Ownership & stewardship",
            "note": null,
            "notes": [],
            "value": 57,
            "inputs": {
              "followers": 2,
              "owner_type": "Organization",
              "is_verified": null,
              "owner_login": "Open-Tech-Foundation",
              "public_repos": 41,
              "account_age_days": 2653
            },
            "components": [
              {
                "key": "ownership_backing",
                "name": "Ownership backing",
                "detail": "organization-owned",
                "points": 30,
                "status": "met",
                "details": [
                  {
                    "code": "owner_organization",
                    "params": {}
                  }
                ],
                "max_points": 30
              },
              {
                "key": "verified_domain",
                "name": "Verified domain",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 20
              },
              {
                "key": "owner_reach",
                "name": "Owner reach",
                "detail": "2 followers of Open-Tech-Foundation",
                "points": 3.4,
                "status": "partial",
                "details": [
                  {
                    "code": "owner_followers",
                    "params": {
                      "count": 2,
                      "login": "Open-Tech-Foundation"
                    }
                  }
                ],
                "max_points": 25
              },
              {
                "key": "track_record",
                "name": "Track record",
                "detail": "41 public repos, account ~7 yr old",
                "points": 23.8,
                "status": "partial",
                "details": [
                  {
                    "code": "public_repos",
                    "params": {
                      "count": 41
                    }
                  },
                  {
                    "code": "account_age_years",
                    "params": {
                      "years": 7
                    }
                  }
                ],
                "max_points": 25
              }
            ]
          },
          {
            "key": "package_maintenance",
            "band": "excellent",
            "name": "Package maintenance",
            "note": null,
            "notes": [],
            "value": 100,
            "inputs": {
              "packages": [
                "@opentf/web",
                "@opentf/web-cli",
                "@opentf/web-docs",
                "@opentf/web-form",
                "@opentf/web-i18n",
                "@opentf/web-test"
              ],
              "ecosystems": "npm",
              "any_deprecated": false,
              "min_days_since_publish": 4
            },
            "components": [
              {
                "key": "published_resolvable",
                "name": "Published & resolvable",
                "detail": "6 package(s) on npm",
                "points": 25,
                "status": "met",
                "details": [
                  {
                    "code": "packages_published",
                    "params": {
                      "count": 6,
                      "ecosystems": "npm"
                    }
                  }
                ],
                "max_points": 25
              },
              {
                "key": "publish_recency",
                "name": "Publish recency",
                "detail": "latest publish 4 days ago",
                "points": 35,
                "status": "met",
                "details": [
                  {
                    "code": "publish_recency",
                    "params": {
                      "days": 4
                    }
                  }
                ],
                "max_points": 35
              },
              {
                "key": "version_history",
                "name": "Version history",
                "detail": "22 published versions",
                "points": 20,
                "status": "met",
                "details": [
                  {
                    "code": "published_versions",
                    "params": {
                      "count": 22
                    }
                  }
                ],
                "max_points": 20
              },
              {
                "key": "not_deprecated",
                "name": "Not deprecated",
                "detail": "active, not deprecated or yanked",
                "points": 20,
                "status": "met",
                "details": [
                  {
                    "code": "package_not_deprecated",
                    "params": {}
                  }
                ],
                "max_points": 20
              }
            ]
          }
        ],
        "description": "Will the project survive its people — bus factor, responsiveness, who backs it, and package upkeep?"
      },
      {
        "key": "engineering",
        "band": "good",
        "name": "Engineering Quality",
        "value": 74,
        "weight": 0.2,
        "metrics": [
          {
            "key": "engineering_practices",
            "band": "moderate",
            "name": "Engineering practices",
            "note": null,
            "notes": [],
            "value": 64,
            "inputs": {
              "has_ci": true,
              "has_tests": true,
              "has_editorconfig": false,
              "has_linter_config": false,
              "has_precommit_config": false
            },
            "components": [
              {
                "key": "ci_workflows",
                "name": "CI workflows",
                "detail": "2 workflow(s)",
                "points": 24,
                "status": "met",
                "details": [
                  {
                    "code": "ci_workflows",
                    "params": {
                      "count": 2
                    }
                  }
                ],
                "max_points": 24
              },
              {
                "key": "tests_present",
                "name": "Tests present",
                "detail": null,
                "points": 24,
                "status": "met",
                "details": [],
                "max_points": 24
              },
              {
                "key": "linter_config",
                "name": "Linter config",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 16
              },
              {
                "key": "pre_commit_hooks",
                "name": "Pre-commit hooks",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 9.6
              },
              {
                "key": "editorconfig",
                "name": ".editorconfig",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 6.4
              },
              {
                "key": "openssf_scorecard_ci_tests",
                "name": "OpenSSF Scorecard: CI-Tests",
                "detail": "4 out of 5 merged PRs checked by a CI test -- score normalized to 8",
                "points": 16,
                "status": "partial",
                "details": [],
                "max_points": 20
              }
            ]
          },
          {
            "key": "documentation",
            "band": "excellent",
            "name": "Documentation",
            "note": null,
            "notes": [],
            "value": 90,
            "inputs": {
              "topics": [
                "api",
                "app",
                "framework",
                "jsx",
                "reactive",
                "signals",
                "web",
                "webcomponent"
              ],
              "has_wiki": false,
              "homepage": "https://web.opentechf.org/",
              "has_readme": true,
              "has_docs_dir": true,
              "has_description": true
            },
            "components": [
              {
                "key": "readme",
                "name": "README",
                "detail": null,
                "points": 30,
                "status": "met",
                "details": [],
                "max_points": 30
              },
              {
                "key": "documentation_directory",
                "name": "Documentation directory",
                "detail": null,
                "points": 25,
                "status": "met",
                "details": [],
                "max_points": 25
              },
              {
                "key": "documentation_homepage_site",
                "name": "Documentation / homepage site",
                "detail": "https://web.opentechf.org/",
                "points": 15,
                "status": "met",
                "details": [],
                "max_points": 15
              },
              {
                "key": "repository_description",
                "name": "Repository description",
                "detail": null,
                "points": 10,
                "status": "met",
                "details": [],
                "max_points": 10
              },
              {
                "key": "topics",
                "name": "Topics",
                "detail": "8 topics",
                "points": 10,
                "status": "met",
                "details": [
                  {
                    "code": "topics_count",
                    "params": {
                      "count": 8
                    }
                  }
                ],
                "max_points": 10
              },
              {
                "key": "wiki",
                "name": "Wiki",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 10
              }
            ]
          }
        ],
        "description": "Are baseline engineering and documentation practices in place?"
      },
      {
        "key": "security",
        "band": "at_risk",
        "name": "Security",
        "value": 30,
        "weight": 0.16,
        "metrics": [
          {
            "key": "security_posture",
            "band": "at_risk",
            "name": "Security posture",
            "note": "Excluded from scoring (no data or not applicable): Packaging, Signed-Releases. Remaining weights renormalized.",
            "notes": [
              {
                "code": "excluded_no_data",
                "params": {
                  "components": [
                    "packaging",
                    "signed_releases"
                  ]
                }
              },
              {
                "code": "weights_renormalized",
                "params": {}
              }
            ],
            "value": 30,
            "inputs": {
              "source": "openssf_scorecard",
              "checks_evaluated": 16,
              "scorecard_version": "v5.5.0",
              "checks_inconclusive": 2,
              "scorecard_aggregate": 3
            },
            "components": [
              {
                "key": "binary_artifacts",
                "name": "Binary-Artifacts",
                "detail": "binaries present in source code",
                "points": 6,
                "status": "partial",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "branch_protection",
                "name": "Branch-Protection",
                "detail": "branch protection not enabled on development/release branches",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "ci_tests",
                "name": "CI-Tests",
                "detail": "4 out of 5 merged PRs checked by a CI test -- score normalized to 8",
                "points": 2,
                "status": "partial",
                "details": [],
                "max_points": 2.5
              },
              {
                "key": "cii_best_practices",
                "name": "CII-Best-Practices",
                "detail": "no effort to earn an OpenSSF best practices badge detected",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 2.5
              },
              {
                "key": "code_review",
                "name": "Code-Review",
                "detail": "Found 0/25 approved changesets -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "contributors",
                "name": "Contributors",
                "detail": "project has 0 contributing companies or organizations -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 2.5
              },
              {
                "key": "dangerous_workflow",
                "name": "Dangerous-Workflow",
                "detail": "no dangerous workflow patterns detected",
                "points": 10,
                "status": "met",
                "details": [],
                "max_points": 10
              },
              {
                "key": "dependency_update_tool",
                "name": "Dependency-Update-Tool",
                "detail": "no update tool detected",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "fuzzing",
                "name": "Fuzzing",
                "detail": "project is not fuzzed",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 5
              },
              {
                "key": "license",
                "name": "License",
                "detail": "license file detected",
                "points": 2.5,
                "status": "met",
                "details": [],
                "max_points": 2.5
              },
              {
                "key": "maintained",
                "name": "Maintained",
                "detail": "30 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10",
                "points": 7.5,
                "status": "met",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "packaging",
                "name": "Packaging",
                "detail": "packaging workflow not detected",
                "points": 0,
                "status": "excluded",
                "details": [
                  {
                    "code": "no_data",
                    "params": {}
                  }
                ],
                "max_points": 5
              },
              {
                "key": "pinned_dependencies",
                "name": "Pinned-Dependencies",
                "detail": "dependency not pinned by hash detected -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 5
              },
              {
                "key": "sast",
                "name": "SAST",
                "detail": "SAST tool is not run on all commits -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 5
              },
              {
                "key": "security_policy",
                "name": "Security-Policy",
                "detail": "security policy file not detected",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 5
              },
              {
                "key": "signed_releases",
                "name": "Signed-Releases",
                "detail": "no releases found",
                "points": 0,
                "status": "excluded",
                "details": [
                  {
                    "code": "no_data",
                    "params": {}
                  }
                ],
                "max_points": 7.5
              },
              {
                "key": "token_permissions",
                "name": "Token-Permissions",
                "detail": "detected GitHub workflow tokens with excessive permissions",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "vulnerabilities",
                "name": "Vulnerabilities",
                "detail": "19 existing vulnerabilities detected",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              }
            ]
          }
        ],
        "description": "Are visible security and supply-chain practices strong, with no malicious dependency and no unresolved high-risk jurisdiction exposure?"
      },
      {
        "key": "ai_readiness",
        "band": "good",
        "name": "AI Readiness",
        "value": 71,
        "weight": 0,
        "metrics": [
          {
            "key": "ai_agent_context",
            "band": "excellent",
            "name": "Agent context & guidance",
            "note": null,
            "notes": [],
            "value": 85,
            "inputs": {
              "has_llms_txt": false,
              "legible_history_share": 1,
              "agent_instruction_files": [
                "AGENTS.md"
              ],
              "agent_instruction_max_bytes": 274
            },
            "components": [
              {
                "key": "agent_instructions",
                "name": "Agent instructions",
                "detail": "AGENTS.md",
                "points": 45,
                "status": "met",
                "details": [
                  {
                    "code": "file_list",
                    "params": {
                      "files": "AGENTS.md"
                    }
                  }
                ],
                "max_points": 45
              },
              {
                "key": "machine_readable_docs_llms_txt",
                "name": "Machine-readable docs (llms.txt)",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 15
              },
              {
                "key": "legible_commit_history",
                "name": "Legible commit history",
                "detail": "100 of 100 human commits state their intent (structured subject or explanatory body)",
                "points": 40,
                "status": "met",
                "details": [
                  {
                    "code": "legible_history",
                    "params": {
                      "legible": 100,
                      "sampled": 100
                    }
                  }
                ],
                "max_points": 40
              }
            ]
          },
          {
            "key": "ai_verify_loop",
            "band": "moderate",
            "name": "Verify loop (build / test / typecheck)",
            "note": null,
            "notes": [],
            "value": 56,
            "inputs": {
              "has_nix": false,
              "has_tests": true,
              "lockfiles": [
                "Cargo.lock"
              ],
              "has_dockerfile": false,
              "typed_language": false,
              "bootstrap_files": [],
              "has_devcontainer": false,
              "has_linter_config": false,
              "typecheck_configs": [
                "packages/create-web/templates/docs/jsconfig.json",
                "packages/create-web/templates/fullstack/jsconfig.json",
                "packages/create-web/templates/library/jsconfig.json",
                "packages/create-web/templates/spa/jsconfig.json",
                "tsconfig.json"
              ],
              "agent_commit_share": 0,
              "toolchain_manifests": [
                "Cargo.toml",
                "crates/otfw_cli/Cargo.toml",
                "crates/otfw_compiler/Cargo.toml",
                "crates/otfw_ir/Cargo.toml"
              ],
              "dependency_bot_commit_share": 0
            },
            "components": [
              {
                "key": "one_command_bootstrap",
                "name": "One-command bootstrap",
                "detail": "Cargo.toml, crates/otfw_cli/Cargo.toml, crates/otfw_compiler/Cargo.toml (toolchain convention, no task runner)",
                "points": 12.6,
                "status": "partial",
                "details": [
                  {
                    "code": "toolchain_convention",
                    "params": {
                      "files": "Cargo.toml, crates/otfw_cli/Cargo.toml, crates/otfw_compiler/Cargo.toml"
                    }
                  }
                ],
                "max_points": 18
              },
              {
                "key": "automated_tests",
                "name": "Automated tests",
                "detail": null,
                "points": 22,
                "status": "met",
                "details": [],
                "max_points": 22
              },
              {
                "key": "lint_format_config",
                "name": "Lint / format config",
                "detail": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 11
              },
              {
                "key": "static_type_checking",
                "name": "Static type checking",
                "detail": "packages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json",
                "points": 11,
                "status": "met",
                "details": [
                  {
                    "code": "file_list",
                    "params": {
                      "files": "packages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json"
                    }
                  }
                ],
                "max_points": 11
              },
              {
                "key": "reproducible_environment",
                "name": "Reproducible environment",
                "detail": "lockfile",
                "points": 10,
                "status": "met",
                "details": [
                  {
                    "code": "file_list",
                    "params": {
                      "files": "lockfile"
                    }
                  }
                ],
                "max_points": 10
              },
              {
                "key": "demonstrated_agent_practice",
                "name": "Demonstrated agent practice",
                "detail": "no agent-authored commits among the last 100",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "no_agent_authored_commits",
                    "params": {
                      "sampled": 100
                    }
                  }
                ],
                "max_points": 10
              },
              {
                "key": "automated_maintenance",
                "name": "Automated maintenance",
                "detail": "no automated dependency updates observed",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "no_dependency_automation",
                    "params": {}
                  }
                ],
                "max_points": 8
              },
              {
                "key": "openssf_scorecard_pinned_dependencies",
                "name": "OpenSSF Scorecard: Pinned-Dependencies",
                "detail": "dependency not pinned by hash detected -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 10
              }
            ]
          },
          {
            "key": "ai_code_legibility",
            "band": "good",
            "name": "Code legibility for models",
            "note": null,
            "notes": [],
            "value": 82,
            "inputs": {
              "primary_language": "JavaScript",
              "largest_source_bytes": 139665,
              "source_files_sampled": 326,
              "oversized_source_files": 3
            },
            "components": [
              {
                "key": "type_checkable_code",
                "name": "Type-checkable code",
                "detail": "JavaScript with type-check config (packages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json)",
                "points": 27,
                "status": "partial",
                "details": [
                  {
                    "code": "typecheck_config_language",
                    "params": {
                      "files": "packages/create-web/templates/docs/jsconfig.json, packages/create-web/templates/fullstack/jsconfig.json, packages/create-web/templates/library/jsconfig.json, packages/create-web/templates/spa/jsconfig.json, tsconfig.json",
                      "language": "JavaScript"
                    }
                  }
                ],
                "max_points": 45
              },
              {
                "key": "manageable_file_sizes",
                "name": "Manageable file sizes",
                "detail": "3/326 source files over 60KB",
                "points": 54.5,
                "status": "partial",
                "details": [
                  {
                    "code": "oversized_source_files",
                    "params": {
                      "kb": 60,
                      "sampled": 326,
                      "oversized": 3
                    }
                  }
                ],
                "max_points": 55
              }
            ]
          }
        ],
        "description": "How well is the repo equipped to be developed and maintained with AI coding agents? An independent, experimental badge — weight 0.0, so it is surfaced on its own and does not affect the overall health score."
      }
    ],
    "metrics_version": "1.13.0"
  },
  "warnings": [
    "Could not fetch crates package 'otfw_ir' from its registry",
    "Could not fetch crates package 'otfw_cli' from its registry",
    "GitHub dependency-graph SBOM unavailable (404); the dependency graph may be disabled for this repository"
  ],
  "report_type": "repository",
  "generated_at": "2026-07-23T21:57:14.722439Z",
  "schema_version": "0.27.0",
  "badge_url": "https://raw.githubusercontent.com/inspect-software/badges/main/v1/o/Open-Tech-Foundation/Web-App-Framework.svg",
  "full_name": "Open-Tech-Foundation/Web-App-Framework",
  "license_state": "standard",
  "license_spdx": "MIT"
}

Las puntuaciones son señales, no garantías. Reflejan prácticas públicamente visibles en GitHub; no son una auditoría de código ni una garantía de seguridad.

Los datos ausentes se excluyen y los pesos se renormalizan; nunca se puntúan como cero. La metodología es versionada y abierta: métricas v1.13.0, esquema v0.27.0 — metodología completa · wiki de métricas.

Cómo se sitúa un resultado dentro del registro general: estadísticas agregadasnpm.