Registro público
Informe de salud del softwareesquema 0.27.0 · métricas 1.13.0 · 2026-07-28 05:47 UTC

wappsdev / wapps-cli

wapps umbrella CLI — age secrets + Coolify shim + git auto-sync

Go · TypeScriptMIT★ 0 estrellas⑂ 0 forksdesde may 2026Ver en GitHub ↗

wappsdev/wapps-cli tiene un índice de salud de 49 sobre 100, lo que lo sitúa en la banda En riesgo. Su puntuación más alta es AI Readiness (74/100) y la más baja, Community & Adoption (24/100). Se actualizó por última vez hace 14 días. Una sola persona concentra la mayor parte del trabajo reciente.

49
global / 100
En riesgo

Í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.

49
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

wappsdevOrganización
2 seguidores3 repositorios públicosdesde ene 2026

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ón
Gogithub.com/wappsdev/wapps-cliv0.19.0-23hace 14 días

Métricas por categoría

Vitalidad

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

67Moderado · 22% del índice global
Cómo se puntúa
28.8/36Recencia de push — último push hace 14 días
4.8/36Cadencia de commits — 7/52 semanas con commits
17.5/18Volumen de commits — 87 commits en el último año
0/10OpenSSF Scorecard: Maintained — project was created within the last 90 days. Please review its contents carefully
Datos de entrada utilizados
commits_last_year87
human_commit_share1
days_since_last_push14
active_weeks_last_year7
Cómo se puntúa
27/27Publica versiones — 23 versiones publicadas
36/36Recencia de las versiones — última versión hace 14 días
27/27Cadencia de publicación — una versión cada ~4,4 días
0/10OpenSSF Scorecard: Signed-Releases — Project has not signed or included provenance with any releases.
Datos de entrada utilizados
releases_count23
latest_release_tagv0.19.0
releases_from_tagsno
days_since_latest_release14
mean_days_between_releases4,4

Comunidad y Adopción

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

24Crítico · 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

Sostenibilidad y Gobernanza

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

51Moderado · 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
3/10OpenSSF Scorecard: Contributors — project has 1 contributing companies or organizations -- score normalized to 3
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.1/38.3Aceptación de PR — 33/34 PR decididos fusionados
0/15OpenSSF Scorecard: Code-Review — Found 0/26 approved changesets -- score normalized to 0
Datos de entrada utilizados
merged_prs33
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 wappsdev
5.4/25Trayectoria — 3 repos públicos, cuenta de ~0 años
Datos de entrada utilizados
followers2
owner_typeOrganization
is_verified
owner_loginwappsdev
public_repos3
account_age_days194
Cómo se puntúa
25/25Publicado y resoluble — 1 paquete(s) en go
35/35Recencia de publicación — última publicación hace 14 días
20/20Historial de versiones — 23 versiones en el registro
20/20No obsoleto — activo, ni obsoleto ni retirado
Datos de entrada utilizados
packagesgithub.com/wappsdev/wapps-cli
ecosystemsgo
any_deprecatedno
min_days_since_publish14

Calidad de Ingeniería

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

67Moderado · 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
20/20OpenSSF Scorecard: CI-Tests — 20 out of 20 merged PRs checked by a CI test -- score normalized to 10
Datos de entrada utilizados
has_ci
has_tests
has_editorconfigno
has_linter_configno
has_precommit_configno

Documentación

65Moderado
Cómo se puntúa
30/30README
25/25Directorio de documentación
0/15Sitio de documentación / página del proyecto
10/10Descripción del repositorio
0/10Topics
0/10Wiki
Datos de entrada utilizados
topics
has_wikino
homepage
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?

27Crítico · 16% del índice global
Cómo se puntúa
7.5/7.5Binary-Artifacts — no binaries found in the repo
0/7.5Branch-Protection — branch protection not enabled on development/release branches
2.5/2.5CI-Tests — 20 out of 20 merged PRs checked by a CI test -- score normalized to 10
0/2.5CII-Best-Practices — no effort to earn an OpenSSF best practices badge detected
0/7.5Code-Review — Found 0/26 approved changesets -- score normalized to 0
0.8/2.5Contributors — project has 1 contributing companies or organizations -- score normalized to 3
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
0/7.5Maintained — project was created within the last 90 days. Please review its contents carefully
5/5Packaging — packaging workflow detected
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 — Project has not signed or included provenance with any releases.
0/7.5Token-Permissions — detected GitHub workflow tokens with excessive permissions
0/7.5Vulnerabilities — 30 existing vulnerabilities detected
Datos de entrada utilizados
sourceopenssf_scorecard
checks_evaluated18
scorecard_versionv5.5.0
checks_inconclusive0
scorecard_aggregate2,7

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.

74Bueno · 0% del índice global
Cómo se puntúa
45/45Instrucciones para agentes — .cursorrules
0/15Documentación legible por máquinas (llms.txt)
40/40Historial de commits legible — 87 de 87 commits humanos declaran su intención (asunto estructurado o cuerpo explicativo)
Datos de entrada utilizados
has_llms_txtno
legible_history_share1
agent_instruction_files.cursorrules
agent_instruction_max_bytes1639
Cómo se puntúa
12.6/18Arranque con un solo comando — go.mod (convención del toolchain, sin ejecutor de tareas)
22/22Pruebas automatizadas
0/11Configuración de lint / formato
11/11Verificación estática de tipos — worker/tsconfig.json
10/10Entorno reproducible — lockfile
0/10Práctica demostrada con agentes — ningún commit con autoría de agente entre los últimos 87
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
lockfilesgo.sum
has_dockerfileno
typed_language
bootstrap_files
has_devcontainerno
has_linter_configno
typecheck_configsworker/tsconfig.json
agent_commit_share0
toolchain_manifestsgo.mod
dependency_bot_commit_share0
Cómo se puntúa
45/45Código verificable por tipos — Go (tipado estático)
55/55Tamaños de archivo manejables — 0/199 archivos fuente de más de 60 KB
Datos de entrada utilizados
primary_languageGo
largest_source_bytes35.832
source_files_sampled199
oversized_source_files0

Datos clave

0estrellas de GitHub
1contribuidores
87commits en los últimos 12 meses
14días desde el último push
23versiones publicadas
1factor bus
0issues abiertas
Go, npmecosistemas de paquetes

Advertencias de recopilación de datos

  • GitHub dependency-graph SBOM unavailable (404); the dependency graph may be disabled for this repository

Más detalle

OpenSSF Scorecard 2.7 / 10
2.7agregado

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-28 05:47 UTC

10Binary-Artifactsno binaries found in the repo
0Branch-Protectionbranch protection not enabled on development/release branches
10CI-Tests20 out of 20 merged PRs checked by a CI test -- score normalized to 10
0CII-Best-Practicesno effort to earn an OpenSSF best practices badge detected
0Code-ReviewFound 0/26 approved changesets -- score normalized to 0
3Contributorsproject has 1 contributing companies or organizations -- score normalized to 3
10Dangerous-Workflowno dangerous workflow patterns detected
0Dependency-Update-Toolno update tool detected
0Fuzzingproject is not fuzzed
10Licenselicense file detected
0Maintainedproject was created within the last 90 days. Please review its contents carefully
10Packagingpackaging workflow 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
0Signed-ReleasesProject has not signed or included provenance with any releases.
0Token-Permissionsdetected GitHub workflow tokens with excessive permissions
0Vulnerabilities30 existing vulnerabilities detected
Dependencias directas 8
RegistroPaqueteRestricción de versiónManifiesto
Gofilippo.io/agev1.3.1go.mod
Gogithub.com/spf13/cobrav1.10.2go.mod
Gogithub.com/stretchr/testifyv1.11.1go.mod
Gogolang.org/x/cryptov0.45.0go.mod
Gogolang.org/x/termv0.37.0go.mod
Gogopkg.in/yaml.v3v3.0.1go.mod
npm@noble/ciphers2.0.1worker/package.json
npm@noble/hashes^1.8.0worker/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": [],
      "is_fork": false,
      "size_kb": 1097,
      "has_wiki": false,
      "homepage": null,
      "languages": {
        "Go": 972389,
        "TypeScript": 360441
      },
      "pushed_at": "2026-07-13T13:02:57Z",
      "created_at": "2026-05-25T17:20:55Z",
      "owner_type": "Organization",
      "updated_at": "2026-07-13T13:04:18Z",
      "description": "wapps umbrella CLI — age secrets + Coolify shim + git auto-sync",
      "is_archived": false,
      "is_disabled": false,
      "license_spdx": "MIT",
      "default_branch": "main",
      "license_spdx_raw": "MIT",
      "primary_language": "Go",
      "significant_languages": [
        "Go",
        "TypeScript"
      ]
    },
    "owner": {
      "blog": null,
      "name": null,
      "type": "Organization",
      "login": "wappsdev",
      "company": null,
      "location": null,
      "followers": 2,
      "avatar_url": "https://avatars.githubusercontent.com/u/254932202?v=4",
      "created_at": "2026-01-14T15:11:17Z",
      "is_verified": null,
      "public_repos": 3,
      "account_age_days": 194
    },
    "license": {
      "state": "standard",
      "spdx_id": "MIT",
      "raw_spdx": "MIT",
      "file_present": true,
      "scorecard_found": true,
      "profile_has_license": true
    },
    "activity": {
      "releases": [
        {
          "tag": "v0.19.0",
          "kind": "minor",
          "published_at": "2026-07-13T12:33:11Z"
        },
        {
          "tag": "v0.18.0",
          "kind": "minor",
          "published_at": "2026-07-13T10:29:36Z"
        },
        {
          "tag": "v0.17.2",
          "kind": "patch",
          "published_at": "2026-07-12T00:13:41Z"
        },
        {
          "tag": "v0.17.1",
          "kind": "patch",
          "published_at": "2026-07-11T23:34:42Z"
        },
        {
          "tag": "v0.17.0",
          "kind": "minor",
          "published_at": "2026-07-11T23:13:51Z"
        },
        {
          "tag": "v0.16.1",
          "kind": "patch",
          "published_at": "2026-07-01T11:32:56Z"
        },
        {
          "tag": "v0.16.0",
          "kind": "minor",
          "published_at": "2026-06-28T20:00:58Z"
        },
        {
          "tag": "v0.15.0",
          "kind": "minor",
          "published_at": "2026-06-09T15:08:25Z"
        },
        {
          "tag": "v0.14.1",
          "kind": "patch",
          "published_at": "2026-06-04T21:35:03Z"
        },
        {
          "tag": "v0.14.0",
          "kind": "minor",
          "published_at": "2026-06-03T20:16:18Z"
        },
        {
          "tag": "v0.13.2",
          "kind": "patch",
          "published_at": "2026-05-28T21:23:18Z"
        },
        {
          "tag": "v0.13.1",
          "kind": "patch",
          "published_at": "2026-05-28T20:37:17Z"
        },
        {
          "tag": "v0.13.0",
          "kind": "minor",
          "published_at": "2026-05-28T18:45:57Z"
        },
        {
          "tag": "v0.12.0",
          "kind": "minor",
          "published_at": "2026-05-28T14:14:04Z"
        },
        {
          "tag": "v0.11.1",
          "kind": "patch",
          "published_at": "2026-05-28T04:03:18Z"
        },
        {
          "tag": "v0.11.0",
          "kind": "minor",
          "published_at": "2026-05-28T03:37:09Z"
        },
        {
          "tag": "v0.5.1",
          "kind": "patch",
          "published_at": "2026-05-26T00:36:19Z"
        },
        {
          "tag": "v0.5.0",
          "kind": "minor",
          "published_at": "2026-05-26T00:27:49Z"
        },
        {
          "tag": "v0.4.0",
          "kind": "minor",
          "published_at": "2026-05-26T00:00:39Z"
        },
        {
          "tag": "v0.3.1",
          "kind": "patch",
          "published_at": "2026-05-25T22:31:46Z"
        },
        {
          "tag": "v0.3.0",
          "kind": "minor",
          "published_at": "2026-05-25T22:28:45Z"
        },
        {
          "tag": "v0.2.0",
          "kind": "minor",
          "published_at": "2026-05-25T19:07:17Z"
        },
        {
          "tag": "v0.1.0",
          "kind": "minor",
          "published_at": "2026-05-25T18:56:51Z"
        }
      ],
      "recent_commits": [
        {
          "oid": "db07ff7e9202b19860ea58cf411672589d122c8c",
          "body": "….19.0+) (#34)",
          "is_bot": false,
          "headline": "docs(skill): add `wapps tofu` to the embedded wapps-secrets skill (v0…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-13T13:02:57Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "60c8da713e506be162effe84ff37286a648ec501",
          "body": "… exec --prefix '' -- tofu` (#33)\n\n`wapps secrets exec --project X --prefix '' -- tofu apply` üç ayrı parça istiyordu\nve kafa karıştırıyordu: `--project` (cwd `.wapps.yaml`'dan zaten çözülür), `--prefix ''`\n(gerekli ama tuzak — store anahtarları tam isimle durur, TF_VAR_ default'u çift-prefix\nyapard\n[…]\nthrough verbatim, verbatim-prefix (çift-prefix yok), scrub,\n  store+legacy backend, F1 regresyon (UnpinnedRefused: exfiltration bloke + service-token\n  exempt + legacy no-op). go build/vet/test yeşil.",
          "is_bot": false,
          "headline": "feat(cli): add `wapps tofu` — clean first-class wrapper over `secrets…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-13T12:31:55Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "2da78e23260b09b940527b3a93f7bf8cdd327c1f",
          "body": "…dr bootstrap + epoch-reset, mTLS, worker replication (#32)\n\n* feat(worker): audit-head route, per-key alert-on-read, state replication + SchedulerDO\n\nZero-git store hedef mimarisinin (docs/wapps-secrets-zero-git-architecture.md)\nWorker tarafı — Faz 2 + P1.4/P1.11:\n\n- GET /v1/audit/head: AuditLogDO'\n[…]\np); tofu.BootstrapEnvVars kataloğu (preflight superset invariant'ı).\n\nTF_VAR_state_passphrase kontratı (backend.tf encryption bloğu var.state_passphrase\nokur) — F3 recovery TF_ENCRYPTION inline değil.",
          "is_bot": false,
          "headline": "feat(secrets): zero-git store core — deploy/dr/coolify store-backed, …",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-13T09:57:53Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "af19fe566660a021b1e9cdf49cc2d5e702a1df13",
          "body": "…ody (#31)\n\n* feat(secrets): dr split / dr combine — MASTER_KEK Shamir offline custody\n\nThe server-decrypt store's only root secret is the MASTER_KEK (a live wrangler Worker\nsecret). There was a way to RESTORE from Shamir shares (dr restore) but no way to\nCREATE them. Add:\n- 'wapps dr split' — takes\n[…]\ny + shares (parity with split) and warns\nthat the printed kid MUST be compared before use (too few/mismatched shares yield a\nsilently-wrong key). --master-hex help notes the ps/shell-history exposure.",
          "is_bot": false,
          "headline": "feat(secrets): dr split / dr combine — MASTER_KEK Shamir offline cust…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-12T00:12:37Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "381161f3877b656aaa98f3ce9a3f10efdb91f0b5",
          "body": "…backend (#30)\n\nThe embedded agent skill only described the legacy git-age archive. Add store-backend\nawareness (both backends, same apply-only commands; wapps login for the store; auth-\nerror → login vs passphrase) so agents don't suggest passphrase/sync flows on migrated\nprojects. Apply-only safety rule + what-not-to-do unchanged. Asset + .claude copy synced.",
          "is_bot": false,
          "headline": "docs(skill): update wapps-secrets skill for the server-decrypt store …",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T23:33:40Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "8a48942c37da9495ae98fad81b55ccb4cdaea247",
          "body": "…dedWallTime) (#29)\n\n* fix(secrets): parallelize writer-DO blob writes (bulk import exceededWallTime)\n\nA 156-key migration import 500'd (error 1101, exceededWallTime) because the writer\nDO wrote blobs SEQUENTIALLY — 156 awaited HEAD+PUT round-trips (~312 serial R2 ops)\nblew the DO wall-time budget. \n[…]\novery text (not re-auth)\n\ncodex P3: NOT_AVAILABLE's registry recovery is about needing a live CF Access session,\nwhich misleads on an oversized read. WithRecovery overrides it to 'request fewer keys'.",
          "is_bot": false,
          "headline": "fix(secrets): parallelize bulk write/read R2 fan-out (migration excee…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T21:38:30Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "d352a4a6f5e880ddbfdd88ce2e0583e2bc0a6237",
          "body": "… fold case (#28)\n\n* fix(secrets): accept POSIX env-var key names (mixed case), not upper-only\n\nKEYNAME_RE was /^[A-Z][A-Z0-9_]{0,127}$/ (upper-only), which rejected the real\ninfra secrets the store must hold: tofu vars whose names are CONTRACTUAL\n(TF_VAR_cloudflare_api_token → var.cloudflare_api_to\n[…]\ned POSIX-env-var KEYNAME_RE, __proto__\nrejection, deny-side folding (enforcement + linter canMatchProd/deniedByRule).\nTests updated: allow case-sensitive, deny case-insensitive, mixed-case round-trip.",
          "is_bot": false,
          "headline": "fix(secrets): accept POSIX env-var key names (mixed case); deny globs…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T20:05:29Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "6b0e0ea55b56e6113c6c85da0ec5cacedb7a8da2",
          "body": "…t callback) (#27)\n\n* fix(secrets): wapps login via cloudflared (CF Access rejects localhost callback)\n\nThe CF Access CLI flow does not support a localhost-callback redirect_url — it\nreturns 'Invalid redirect URL'. The only supported browser flow is edge token\ntransfer (redirect to the app's own dom\n[…]\ne generic live-session advice. Add cloudflared\nto runDoctorFull's dependency scan and override the error Recovery with a platform-\nneutral install instruction so operators get an actionable next step.",
          "is_bot": false,
          "headline": "fix(secrets): wapps login via cloudflared (CF Access rejects localhos…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T18:36:53Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "759133a25c2179d3feff175926ca64567c1fd725",
          "body": "…n't advertise the store) (#26)\n\nThe secret-store hostname openly advertised its function (recon signal). Renamed to a neutral\ngw.meapps.dev / gw-staging.meapps.dev (defense-in-depth; the real controls stay CF Access + crypto).\nCLI DefaultGateURL, wrangler custom_domain routes, comments + tests updated. Access app AUDs unchanged\n(per-app). Live CF change already applied (Access app domains + worker custom domains re-pointed;\nold secrets.* removed). Bucket names (wapps-secrets-*) unchanged.",
          "is_bot": false,
          "headline": "chore(secrets): rename gate hostname secrets→gw.meapps.dev (opsec: do…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T17:38:48Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "d2d171d6480594270ebf2991f8d390ad5ed24fd4",
          "body": "…deploy (#25)\n\nProd Worker (secrets-gate) deployed live: real prod bindings (wapps-secrets-prod R2, audit_prod D1\nf33848e6, jti/rate/IDENTITY_CACHE_prod KV), ACCESS_AUD_READ/WRITE, ADMIN_EMAILS=adnan@wapps.co,\nteam domain wapps-dev.cloudflareaccess.com, custom_domain secrets.meapps.dev, crons remove\n[…]\nped to R2 (developers→all read/write, admins→*, infra→+rotate). secrets.meapps.dev\nis CF-Access-gated (302 → Google SSO). Deployed via wrangler + workers/domains API (token lacks Workers Routes:Edit).",
          "is_bot": false,
          "headline": "chore(secrets): wire prod wrangler.jsonc for the live server-decrypt …",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T17:29:04Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "2a519abeb0d14de1d447d9252ec35ea21b18a893",
          "body": "…oup-gated store (#24)\n\n* feat(secrets): server-decrypt Worker core — CF-Access + Google-group gated (pivot from zero-knowledge)\n\nPivots the Worker from zero-knowledge (per-key X25519 wraps + M-of-N roster) to server-side decryption\ngated by CF Access + Google Workspace groups, per the SPEC-READY sp\n[…]\npath):\nexport completeness proof still trusts IsRootAdmin (root reads are also policy-filtered) + import --confirm can\nbe bypassed for write-only-readable keys. To harden before the real prod cutover.",
          "is_bot": false,
          "headline": "feat(secrets): server-decrypt pivot — CF Access + Google Workspace gr…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T17:13:22Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e937aca9af63b8658ffc44faeb7839f294cab9b0",
          "body": "…ging deploy config (#23)\n\nCF Workers Free plan rejects new_classes (KV-backed) DOs with code 10097 (\"must use\nnew_sqlite_classes\"). SQLite-backed DOs are the modern default and expose the same state.storage\nAPI (no DO code change), so the migration is a safe, cost-avoiding switch for fresh (never-d\n[…]\nuts (D1/KV/R2 ids, staging\nREAD AUD, team domain) — secrets-gate-staging deployed successfully to workers.dev and fails closed\n(503) pending GENESIS_TRUST_SHA256 + MINT_KEY (set at the root ceremony).",
          "is_bot": false,
          "headline": "fix(worker): SQLite-backed Durable Objects (Free-tier eligible) + sta…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T02:05:43Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "1089def1856205e059e97957ccf9c0d64871e662",
          "body": "…w rounds 1-11) (#22)\n\nPR #21 was squash-merged from a stale branch that predated the codex GPT-5.6 adversarial review\nloop; this lands the full codex-CLEAN hardening (50 files) that was missing from main:\n\n- Go<->TS strict-shape consensus gate + 103-vector cross-language parity oracle (Go verdict =\n[…]\n verdict: CLEAN (round 12). Verified: go build+vet+gofmt clean, go test ./... 28 pkgs ok;\nworker tsc clean, npm test 20 files / 312 tests pass. Tree is identical to the verified tag secrets-codex-r11.",
          "is_bot": false,
          "headline": "fix(secrets): codex-clean consensus + offboard authz hardening (revie…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T00:57:12Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "70adab1384c1b81e539a4274a420e84a324bf238",
          "body": "…) (#21)\n\n* feat(secrets): crypto core — cryptoid + manifest (G2)\n\ninternal/cryptoid: X25519 encryption identities (+ plugin recipient parsing +\noffline fingerprints), separate Ed25519/ECDSA-P256 detached signing over exact\nbytes (verify-before-parse), per-key DEK envelope (XChaCha20-Poly1305, bucke\n[…]\n); set->get round-trip; enroll reload/sign proof.\n\nGo build + touched-pkg tests green; the real login remains the only account-gated step.\n(pre-existing gofmt/lint debt in untouched files left alone.)",
          "is_bot": false,
          "headline": "feat(secrets): git-free Cloudflare-native secret store (wapps-secrets…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-11T00:50:48Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "49a3f2fa0b27122f6cb761d16ed5f32f416aa592",
          "body": "wapps secrets exec/env prepended the .wapps.yaml source prefix (default\nTF_VAR_) to every archive key unconditionally. A key stored already-prefixed\n(e.g. TF_VAR_gemini_api_key, set directly into the archive rather than derived\nfrom a Tofu output) became TF_VAR_TF_VAR_gemini_api_key and never reache\n[…]\n(env,\nall three value branches). find-bugs clean.\n\nTests: TestEnvName_Idempotent + TestBuildExecEnv_IdempotentPrefix (mixed\narchive: bare key gains prefix, already-prefixed stays verbatim, no double).",
          "is_bot": false,
          "headline": "fix(secrets): idempotent env prefix in exec/env (no double TF_VAR_)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-07-01T11:31:55Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "b86ef3c5dd2f801a97b01a8c90ea889f02409a9b",
          "body": null,
          "is_bot": false,
          "headline": "docs(changelog): cut v0.16.0",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-28T19:59:54Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "d6b665c901b06d4881ab22acda3dd686db1296ac",
          "body": "Implements deploy-tooling-gaps P1 + P4 to the full wapps-deploy-spec,\nvalidated against the proxy server's deploy-proxy/main.go (source of truth).\nGives every non-CI deploy (manual ops, break-glass, an AI agent) a supported\npath instead of hand-reconstructing the pipeline's inline curl + gathering\nc\n[…]\n (env-beats-archive, legacy-fallback, missing-cred,\nunknown-repo, bad-name, e2e trigger, out-of-scope no-poll, migrator --wait,\n--wait+--json single-object, --wait failed single-line, AI-safe golden).",
          "is_bot": false,
          "headline": "feat(deploy): wapps deploy <service> via company-deploy-proxy",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-28T19:59:31Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "8f29ab711dfb7255fbbf43b9f9a4cd75d39060b7",
          "body": null,
          "is_bot": false,
          "headline": "docs(changelog): cut v0.15.0",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-09T15:07:13Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "77b1fbe0695c1151400886a488262f007432c3f4",
          "body": null,
          "is_bot": false,
          "headline": "docs(changelog): wapps skill install",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-09T15:06:50Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "23929758c1a7dd90515460d02e4dd65c6304ca61",
          "body": "…skill\n\nShips the AI-safe wapps-secrets Claude Code skill INSIDE the binary\n(//go:embed) so a Homebrew install — which has no repo checkout — can\ninstall it with no source tree:\n\n  wapps skill install                 user-wide ~/.claude/skills (default)\n  wapps skill install --local --copy  committa\n[…]\ntmp with a fake HOME;\nreal-dir + file-symlink layout confirmed; status/refresh round-trip green.\n9 tests in internal/skill; find-bugs pass (fixed the flag-before-subcommand\nauto-refresh double-print).",
          "is_bot": false,
          "headline": "feat(skill): wapps skill install — embed + install the wapps-secrets …",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-09T15:06:50Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "56d6e7b599057c4c3e8f4cf052c2da49b9a287db",
          "body": null,
          "is_bot": false,
          "headline": "docs(changelog): cut v0.14.1",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-04T21:33:54Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "16da2e7dde291bd97532c214c8a823b192346e45",
          "body": "readKey unmarshaled the entire archive into a map[string]struct{Value string}\nand failed the moment ANY key held a non-string value (e.g. the array\nvaulter_traefik_cert_paths) — crashing 'wapps secrets get <key>' before it\never reached the requested (string) key. import-env'd secrets were thus\nvisib\n[…]\non a string key with an array key present (the crash\nrepro), get on an array key (compact JSON), rawValueToString edge cases\n(null/absent/array/number/bool/object), exec inclusion with/without prefix.",
          "is_bot": false,
          "headline": "fix(get): don't crash on archives containing a non-string value",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-04T21:33:33Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "6a7bc6cd360300a86f4ae510f8e975faeaec71c5",
          "body": null,
          "is_bot": false,
          "headline": "docs(changelog): cut v0.14.0",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-03T20:14:46Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "10a7d680c600eadd79ad4e67043c6a91c778f9be",
          "body": "Standalone before/after explainer + operator runbook for the\n--config/--project / config-dir-relative feature shipping in v0.14.0.\nComplements the architecture.md §3 reference and the onboarding note.",
          "is_bot": false,
          "headline": "docs: dedicated secrets-from-anywhere before/after guide",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-03T20:14:34Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "77cad91f8f2efc4f64ffc82d9f60c8f905f056e8",
          "body": "…ented",
          "is_bot": false,
          "headline": "docs: secrets-from-anywhere (--config/--project) + spec marked implem…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-03T20:14:14Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "80df113b017909ddad6782ad477a635f70e4ba41",
          "body": "--project <name> / -p resolves a registered project from\n~/.config/wapps/projects.yaml (name → dir, XDG-aware, ~ expansion) to its\n.wapps.yaml, then feeds the same configRoot path resolution. Mutually\nexclusive with --config (cobra MarkFlagsMutuallyExclusive + a belt check);\n--config gains -c. Unkno\n[…]\nets.SetConfigPath, and runs the git auto-sync preflight against\nconfigRoot (the project repo) instead of cwd, skipping cleanly when that dir\nisn't a git work tree (Fix 3). Covers acceptance #3 and #6.",
          "is_bot": false,
          "headline": "feat(cli): --project registry + git preflight on configRoot",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-03T20:14:14Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e6b8bdb7aac620292f5701db173ffa697039fb40",
          "body": "…ve site\n\nThe --config flag was dead: every secrets command loaded a hardcoded\n'.wapps.yaml' and resolved the archive against cwd. New package seam —\nSetConfigPath/wappsConfigPath()/configPathOverride — lets root hand the\nresolved config path in; config.Load then records configRoot and the Resolve*\n\n[…]\nented, outside the from-anywhere acceptance set).\n- rotate-master's audit log records the raw relative archive path for parity.\n\nconfigroot_test.go covers acceptance #1,#2,#4,#5,#7 from a foreign cwd.",
          "is_bot": false,
          "headline": "feat(secrets): honor --config/--project via configRoot at every archi…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-03T20:14:14Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "84f80be3a2ea2ee38385653ddd99469f47c77eec",
          "body": "Load now records the absolute directory of the loaded .wapps.yaml as an\nunexported configRoot. New helpers resolve relative paths against it:\nResolveDest, Target.ResolvePath, ResolvedSources (file path + tofu workdir),\nand a general Resolve. Absolute paths and Parse-built configs (configRoot\n\"\") pas\n[…]\nurce with an omitted workdir defaults to configRoot (mapped \"\" →\n\".\") so a --project sync never silently runs 'tofu output' in the operator's\ncwd; file sources keep an empty workdir (they reject one).",
          "is_bot": false,
          "headline": "feat(config): config-dir-relative path resolution",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-06-03T20:14:14Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "6ecf98f2f2033570850f8f021caeb6b712f923a0",
          "body": "ADDENDUM 2: Coolify returns the SAME key twice when an env is defined for\nboth runtime and preview deployments — is_preview=false (production runtime)\nand is_preview=true (per-PR preview), with possibly different values. The\nnaive currentByKey build was last-write-wins, so the preview value (observe\n[…]\no-op.\n\nTests: is_preview parse; preview dup → no change (runtime matches);\norder-independence (runtime wins either way); preview-only key → add not\ncompare. find-bugs: 6 semantics verified, no issues.",
          "is_bot": false,
          "headline": "feat(coolify): ignore is_preview-duplicate envs in the sync diff",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T21:21:56Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "7073eacb8ae7213c91c896a7bd4c34196b3b844b",
          "body": "v0.13.0 was tagged while its content still sat under [Unreleased].\nReconcile: the multi-app sync, update-check, coverage, and hardening\nsweep are v0.13.0 (already shipped); is_coolify filter + exclude_keys\nare v0.13.1 (this release).",
          "is_bot": false,
          "headline": "docs(changelog): split v0.13.0 / v0.13.1 sections",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T20:36:00Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "bdfe2945da0428bcb78f2d4ca59d4d421ed42680",
          "body": "Two diff filters from the multi-app handoff ADDENDUM, so a Coolify sync\nnever fights keys it doesn't own.\n\nis_coolify filter (the high-priority one):\n  Coolify generates read-only 'magic' envs (SERVICE_FQDN_*, SERVICE_URL_*)\n  flagged is_coolify=true. A PATCH against one 422s; under delete_unmanaged\n[…]\nmanaged Coolify-only key not\nremoved; exclude_keys drops + counts only matched; end-to-end multi-app\nskip-and-report. Docs + CHANGELOG updated.\n\nShips in the next release alongside the multi-app work.",
          "is_bot": false,
          "headline": "feat(coolify): skip is_coolify-managed envs + coolify_sync.exclude_keys",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T20:35:03Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "395b3be57112a272456d4e0ed2c0319d064279d0",
          "body": "Canonical 'how the system works' doc covering the data model (sources →\narchive → consumers), the full .wapps.yaml schema, the command surface,\nboth Coolify sync modes, the safety model, what's committed vs gitignored,\nversioning/distribution, and package layout.\n\nComplements the existing task-oriented onboarding.md and chronological\nCHANGELOG.md — this is the reference an engineer reads to understand the\narchitecture before touching it.",
          "is_bot": false,
          "headline": "docs: architecture & reference for the wapps secret system",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T19:43:06Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "eb7e1d231b8fe995b9678e162309cf0509d5d48c",
          "body": "A multi-app archive (one .enc.age holding KREEVA_WEB_*, ROYCO_API_*, ...)\ncan now be pushed back to Coolify with each app receiving only its own\nprefix-matched subset, prefix-stripped, non-destructively by default.\n\nNew surface:\n  wapps secrets sync --target=coolify --all-apps [--force]\n\n.wapps.yaml\n[…]\nation (overlap both orders, dup, missing fields),\narchiveToAppMap (strip/filter/exact-match-skip), per-app subset isolation,\ndelete_unmanaged on/off, dry-run, zero-match skip, apply-failure isolation.",
          "is_bot": false,
          "headline": "feat(coolify): multi-app sync via --all-apps + coolify_sync.apps mapping",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T18:44:28Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "3c2fe3729681c74a95d8aa5e7e7bf3f91b868724",
          "body": "Released binaries now check GitHub's releases-latest endpoint at most once\nper 24h (cached in <user-cache>/wapps/version-check.json) and print a one-\nline upgrade notice on stderr after the command runs.\n\nGating (all intentional):\n  - Only semver-tagged release binaries check. Local builds (Version \n[…]\nd: documents the behavior + opt-out under Step 1.\n\n15 new tests covering semver parse/compare, cache freshness + refetch,\natomic cache write, all error swallow paths, and the escape-injection\ndefense.",
          "is_bot": false,
          "headline": "feat(updatecheck): daily best-effort 'newer release available' notice",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T18:02:56Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "2978d5237cf481f021e090638484cb639eb8377d",
          "body": "…ogic\n\nThe three cmd/coolify commands that hit real API endpoints (deploy-app,\ndeploy-app-git, update-env) had no tests because the runE bodies all\nend in a network call. Each command does have a non-trivial pure-Go\npreflight step that's worth testing:\n\n- update-env: parseEnvKVs() validates --env KE\n[…]\ne c.UpdateAppEnvs / c.CreateDockerComposeApp /\nc.CreatePrivateGitHubAppApp / c.StartApp call sites, which can be\nmocked via the coolifyAPI interface pattern when an end-to-end test\nbecomes a priority.",
          "is_bot": false,
          "headline": "test(coolify): cover deploy-app, deploy-app-git, update-env parsing l…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T14:09:23Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "d241e755f0b58da31ab775a7962bf0d831207f5c",
          "body": "…+ internal layers\n\nEight bugs + one ineffective test, found by a parallel code-reviewer\nsweep and triaged for >70% confidence. Each fix has a dedicated\nregression test that fails on the bug and passes on the fix.\n\n* cmd/secrets/sync_coolify.go: applyCoolifyDiff() now writes the\n  '✓ Applied' line t\n[…]\nd dedupEnvCase already enforces\n    last-wins semantics.\n  - get.go --write flag: by-design operator-only path.\n  - diff.go rotation hint: hint is operationally useful, not a real\n    info-disclosure.",
          "is_bot": false,
          "headline": "fix(secrets,coolify,doctor,git): nine hardening fixes across the cmd …",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T14:09:23Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "f6a6a274e69b65a8dbdc2163948c4297bd22b255",
          "body": "Two atomic-write hardening fixes that came out of the bug-hunt sweep:\n\n1. WriteFileAtomic now uses os.CreateTemp instead of a fixed temp name.\n   The previous '.<base>.tmp' name was deterministic, so two processes\n   writing the same target opened and truncated each other's tmp file.\n   With CreateT\n[…]\nc. A power loss\n   between rename and the kernel's data flush could otherwise leave the\n   .env file present but empty — visible disaster for the team since\n   .env is part of the trusted file source.",
          "is_bot": false,
          "headline": "fix(ageutil,source): unique temp names + fsync in WriteFileSource",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T14:09:23Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ea0fc08e2d1c1895d5bdc10f4f2356ad224211da",
          "body": "…direct\n\nFive hardening fixes in the coolify client package, found by a parallel\ncode-reviewer sweep:\n\n1. validateUUID enforces UUID-shape (or lax slug for test fixtures) on\n   appUUID/envUUID before path concatenation. Closes the URL injection\n   vector where a value like '../servers' would resolve\n[…]\nat the entry of every public method that\n   concatenates appUUID into a URL path (ListAppEnvs, UpsertAppEnv,\n   DeleteAppEnv, UpdateAppEnvs, SetBuildArgs, TriggerDeploy,\n   SetCustomLabels, StartApp).",
          "is_bot": false,
          "headline": "fix(coolify): validate UUIDs, truncate error bodies, strip auth on re…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T14:09:23Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "602eaee8f75ce8eb0fff78fdc9cc0b78ec99e4bb",
          "body": "The previous CI bump raised the job timeout, but 'go test' itself has a\ndefault 10m per-package timeout that was killing cmd/secrets midway\nthrough (it takes ~5m with -race due to scrypt-based age.Encrypt in\nfixtures, plus the -v output keeps it streaming for the full duration).\nPass -timeout 15m so go test waits as long as the job allows.",
          "is_bot": false,
          "headline": "ci: extend go test timeout to 15m (default is 10m)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T13:04:45Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "8fe2dcafd8c91728ede4f60fcc231ce697a4cf36",
          "body": "CI was killing the test job at 10m. The cmd/secrets package alone takes\n~5m with -race due to scrypt-based age.Encrypt in fixtures; the new\napply/diff tests pushed total runtime past the limit.\n\nTwo changes:\n  - .github/workflows/ci.yml: timeout-minutes 10 → 15\n  - cmd/secrets/apply_test.go: remove \n[…]\nded against\n    HFS+ second-granularity mtime. Modern filesystems (ext4 on CI, APFS\n    on dev) resolve mtime at nanosecond precision; two consecutive\n    writes show distinct mtimes without any wait.",
          "is_bot": false,
          "headline": "ci: bump test timeout to 15m, drop coarse-FS sleep in apply tests",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T13:04:45Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "f742c77ea42d9fdea9d6b2e05bd4d813fbfacd01",
          "body": "Onboarding doc covers the apply-first / predev-script workflow and adds\na .wapps.yaml reference with the new sections.\n\nAI skill (SKILL.md) and .cursorrules name 'apply' as the preferred way\nto materialize env files; env --write becomes the ad-hoc fallback.\n\ninit template emits a commented-out 'targets:' block so new repos see\nthe option without having to read the docs first.",
          "is_bot": false,
          "headline": "docs: targets workflow + diff/apply commands",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T13:04:45Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "766bb635a7000ba883a849f72d154ba1346ff0c3",
          "body": "'wapps secrets diff [ref]' compares archive at a git ref (default HEAD~1)\nto the current working tree. Output shows added/changed/removed key\nnames — values, value hashes, and value lengths never reach stdout.\nChange detection uses sha256(canonical value JSON) in-process.\n\nSafety: gitShowRunner refu\n[…]\ns\nref naming rules already forbid leading dashes, so this never rejects\na legitimate ref.\n\nDecrypt failure across the ref hints at passphrase rotation (which the\ncurrent implementation does not span).",
          "is_bot": false,
          "headline": "feat(secrets): diff command (AI-safe, key-only)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T13:04:45Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "9b474b3c009519d68e92723a753dfd02fe9317a4",
          "body": "Adds 'wapps secrets apply' which materializes every target declared in\n.wapps.yaml's 'targets:' block atomically. Idempotent — files already\nmatching the would-be-written bytes are left alone (mtime untouched) so\nfile watchers (Next.js dev server, Vite HMR) don't spuriously reload.\n\nAfter every arch\n[…]\ncommand. Set/import-env are refactored to return the\nmarshaled payload from encryptAndWriteArchive so the apply step reuses\nthe same bytes — avoids double-marshal divergence in key order across\ncalls.",
          "is_bot": false,
          "headline": "feat(secrets): apply command + auto-apply hook for set/import-env/sync",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T13:04:45Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "fafbabccf075238b66c4720b4881da41f78249a0",
          "body": "New optional fields:\n  default_prefix: repo-wide prefix used by 'apply' and per-target overrides\n  targets: declarative consumption file list (path, optional prefix)\n\nTarget.Prefix is *string so 'unset' and 'explicit empty' are distinguishable\n(needed when default_prefix is non-empty but a specific target wants plain).\n\nValidation: target.path required, no duplicates, '..' rejected.",
          "is_bot": false,
          "headline": "feat(config): add default_prefix and targets to .wapps.yaml schema",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T13:04:45Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "c2d7586664a6db42c36a8994337a1e93aca76af1",
          "body": "PROGRESS.md + CHANGELOG.md created to carry session state forward.\nMemory dir bootstrapped at ~/.claude/projects/-Users-adnankurt-Documents-Projects-wapps-cli/memory/\nwith 6 entries (project state, distribution channel, AI skill location,\ndesign doc index, PR pattern preference, cross-repo exploration rule).",
          "is_bot": false,
          "headline": "chore: refresh trackers + memory before compact",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T04:10:01Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "4a40e69a5553a16dd6dbbb1b06d5dae72ec46f7d",
          "body": "Previously 'wapps --version' returned \"unknown flag\" — main.go had no\nversion var to inject into, and the .goreleaser.yml ldflag pointed at\nnonexistent main.version (a silent no-op for every prior release).\n\nThis commit:\n- Adds cmd.Version (default \"dev\") and wires rootCmd.Version, which\n  makes cob\n[…]\nform\n  collision since cobra only adds --version long form when -v is taken\n\nSmoke tests in cmd/root_test.go guard against accidental removal of\nVersion field (which would silently disable --version).",
          "is_bot": false,
          "headline": "fix: wapps --version flag + correct GoReleaser ldflag target",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T04:02:13Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "8f8a9c90dc2e6de88635d1a89762d1e9f5a1737a",
          "body": "Implements eng-review T13 (AI integration) and T14 (operator\nonboarding doc). With this commit and the preceding T8/T11/T12/T15\nwork, B.3 closes — wapps-cli has everything it needs for the first\nteammate rollout.\n\n.claude/skills/wapps-secrets/SKILL.md (T13):\n  Teaches Claude Code / agents the apply-\n[…]\ned):\n  - CONTRIBUTING.md (defer until first external contribution interest)\n  - README polish for public release (defer to v1.0.0)\n  - Anonymization of internal examples (defer to public-repo cutover)",
          "is_bot": false,
          "headline": "docs: AI skill + .cursorrules + operator onboarding (T13 + T14)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T03:23:48Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "f7e2b88850ae10692e23760170294c3e042edb13",
          "body": "Implements eng-review T10. The --target=coolify flag on\n'wapps secrets sync' pushes archive contents to a Coolify application's\nenv vars, with dry-run-by-default + --force destructive (Issue 2 D3\ndecision in office-hours).\n\nUsage:\n  wapps secrets sync --target=coolify --app <uuid>          # dry-run\n[…]\nnoop,\n    archiveToFlatMap string/list/prefix, applyCoolifyDiff ordering,\n    stops on first error)\n\n22 new tests total. SetBuildArgs's 5 existing tests still pass after\nrefactor — abstraction proven.",
          "is_bot": false,
          "headline": "feat(secrets): sync --target=coolify mirrors archive to Coolify app env",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T03:23:48Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "8afd9674d21962c1b8f1d75e932730ce8f7949d3",
          "body": "…pers)\n\nT9 in the eng review was scoped to infra-tofu/projects/platform —\noperational work in a different repo. But the CLI gains two helpers\nhere that make platform bootstrap (and any per-repo rollout) a\none-command affair:\n\n  wapps secrets init [--with-file-source] [--force]\n  wapps doctor --for t\n[…]\nentries, idempotent)\n  - doctor --for tofu covered indirectly via PreflightEnv tests\n    (the same code path)\n\nOnboarding doc (T14 next commit) will reference both as Step 1/2 of\nthe per-repo rollout.",
          "is_bot": false,
          "headline": "feat(secrets,doctor): init scaffolder + doctor --for tofu (T9 CLI hel…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T03:23:48Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "cf922d769c240a84e0aa0af392adba48f6712794",
          "body": "Implements eng-review T11. After every successful rotate-master,\nappends one JSONL line to <archive-dir>/rotation.log recording who\nrotated, when, against which archives, and with what pp fingerprints.\n\nSchema (versioned):\n  schema_version: 1\n  ts: RFC3339 UTC timestamp\n  actor: $USER from os/user.C\n[…]\nacross two rotations, error when pp same, error when old missing,\nerror when new missing, decrypt failure when wrong old pp, fingerprint\ndeterminism + distinctness, key count for valid + invalid JSON.",
          "is_bot": false,
          "headline": "feat(secrets): rotate-master writes audit log JSONL",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T03:23:48Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "9a8109c4c53f31384c8c1d9560332b97ff24d1a4",
          "body": "Implements eng-review T15 — minimal open-source readiness. Public\nrelease (CONTRIBUTING.md, anonymization of internal examples, repo\npublic toggle) deferred until first external interest per design doc.",
          "is_bot": false,
          "headline": "chore: add MIT LICENSE",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T03:23:48Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "57fedcc0225a05dc780505bb91b48aa4b3d8170a",
          "body": "Implements eng-review T8 in the D11-narrowed scope (cmd/secrets/*,\ninternal/source/*, internal/ageutil/* — NOT cmd/coolify/, cmd/git/,\ncmd/doctor.go).\n\nDesign choice (post-Codex critique): EXPLICIT redaction via Wrap()\nrather than heuristic auto-redact. Reasons:\n\n  - Heuristic regex auto-redact has \n[…]\node paths use safelog at call site. Auto-converting existing\nfmt.Errorf calls would change tested behavior and risk regression for\nno current leak (verified: no existing message quotes secret values).",
          "is_bot": false,
          "headline": "feat(safelog): explicit redaction primitives for secret-handling paths",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:44:36Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "d11017a2449ba62562bb5268d42fb5627adff070",
          "body": "Implements eng-review T12: archive writes go through one atomic helper.\nPreviously sync.go and rotate.go used bare os.WriteFile which can leave\na truncated archive on power loss / signal kill — catastrophic for a\nsecrets archive. set.go and import-env.go already did temp+rename\ninline, but with dupl\n[…]\nxisting, no .tmp\nleftover on success, temp in same dir as target (cross-fs safety),\nencrypt+write roundtrip, encrypt failure leaves nothing behind, parent\ndir must exist (no auto-mkdir to hide typos).",
          "is_bot": false,
          "headline": "feat(ageutil): atomic write helper + refactor sync/set/import-env/rotate",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:44:36Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "2d9a5e3d29dda223f789f2d8809187edf15504a3",
          "body": "Implements the exec half of eng-review T7: AI-safe apply primitive that\nruns a subprocess with the decrypted archive injected as env vars. wapps\nitself never prints values; only the subprocess does (and its output is\nthe subprocess's own responsibility — a separate trust boundary).\n\nUsage:\n  wapps s\n[…]\ntedEnvOnCollision (last-wins for archive)\n  - NoPassphraseErrors\n  - EmptyArgsErrors\n  - RunnerErrorPropagates\n  - buildExecEnv: string/list/null value types, sorted order, malformed\n    JSON rejected",
          "is_bot": false,
          "headline": "feat(secrets): exec -- runs commands with archive env injected",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:23:50Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "51135f238876aea3d11fe78c143d81fb88f8ecfa",
          "body": "Implements the env half of eng-review T7: AI-safe apply primitive that\nwrites secrets to a file without printing any value to stdout. Agents\ncall 'wapps secrets env --write .env.local' instead of relying on the\nshell-redirect pattern (which would show values in the agent transcript\nas the captured t\n[…]\nitten file, no .tmp leftover, missing passphrase, and\n.wapps.yaml dest override.\n\nExisting 5 writeTofuOutputsAsEnv tests updated to pass the new prefix\nparameter (preserving TF_VAR_ default behavior).",
          "is_bot": false,
          "headline": "feat(secrets): env --write + --prefix flags for AI-safe writes",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:23:50Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e191744b63b26b9d855dcde075c20426cf5b7110",
          "body": "Implements eng-review T6: 'wapps secrets import-env <file>'. Reuses the\nsame env-file parser the file source adapter uses, so anything that\nimports cleanly via import-env also works as a 'file' source declaration\nin .wapps.yaml (consistency is the whole point of one parser).\n\nUse case: existing repo\n[…]\ntests: happy path with 3 imported + 1 pre-existing keys preserved,\n.wapps.yaml requirement, malformed env file rejected with line N,\nmissing input file error, all-comment file is no-op (not an error).",
          "is_bot": false,
          "headline": "feat(secrets): import-env for one-shot bulk capture into the archive",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:11:39Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "50882e8f5950463199846e682567dd9519533973",
          "body": "Implements eng-review T5: 'wapps secrets set <KEY>' — the capture half of\nthe capture-discipline insight from /office-hours.\n\nSequence:\n  1. Load .wapps.yaml (required — set has no place in legacy tofu-only mode\n     since you can't write back to Tofu state from the CLI)\n  2. Locate single file sour\n[…]\nty drift rejection, drift error propagation, missing\npassphrase, empty value rejection, empty KEY guard, atomic write (no\n.tmp leftover).\n\nDependency: golang.org/x/term v0.43.0 for the no-echo prompt.",
          "is_bot": false,
          "headline": "feat(secrets): set captures new secret values (interactive, no echo)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:11:39Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "e388ca385ab61a0f0c3a542a328ccf86800e2c5a",
          "body": "Adds WriteFileSource which lets cmd/secrets/set update a file source after\ncapturing a new key. Per D6.b (eng-review), file sources are\nmachine-managed: naive sorted key=value form, no comment preservation\n(the team agreed not to use inline comments).\n\nBehavior:\n  - Reads existing entries via the sa\n[…]\nent.\n\n7 tests: new file with header, sorted append across multiple writes,\noverride of existing key, single-quote escape, preservation of existing\nkeys on append, 0600 mode, atomic (no .tmp leftover).",
          "is_bot": false,
          "headline": "feat(source): file writer with sorted naive-write + wapps-managed header",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:11:39Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "33f54aa1dc7942ed25e02650f1ba87374feb11e4",
          "body": "Wires the Source/Config abstraction into wapps secrets sync. Two paths:\n\n1. Legacy (no .wapps.yaml present): unchanged behavior — single tofu\n   source, dest=secrets/all.enc.age, preflight env check. v0.5.x repos\n   continue to work without any operator action.\n\n2. Config-driven (.wapps.yaml present\n[…]\nConfigPath_RejectsBadYAML: malformed config halts, does not\n    silently fall back\n\nRefactored emitCommitHint as a private helper so both paths share the\n\"Next: git add ... && git commit\" advice line.",
          "is_bot": false,
          "headline": "feat(secrets): sync dispatches to .wapps.yaml or legacy tofu",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:01:15Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "69e90eb4ee333defe82f1af07067b2354fd7302c",
          "body": "Builds the abstraction for multi-source secrets (eng-review T4). Each\nSource implementation reads its underlying system (Tofu state, .env file,\nlater: GitHub Secrets, Coolify env) and returns tofu-output-shaped JSON\nthat merges cleanly with other sources.\n\ninternal/source:\n  - Source interface (Name\n[…]\niles. Coverage spans happy paths, all error\nbranches (unknown type, missing fields, mutually-exclusive fields,\nmalformed YAML, malformed env file at line N), and the Merge override\ndetection contract.",
          "is_bot": false,
          "headline": "feat(source,config): introduce Source interface + .wapps.yaml schema",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T02:01:15Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "f545bd2ddcdf3598d3f37dfbc2256285cd015a2a",
          "body": "…ippet\n\n\\`wapps secrets sync\\` shells out to \\`tofu output -json\\`, which reads\nprovider creds + state-backend creds at startup. Missing env vars\npreviously produced confusing tofu errors that didn't point at the fix:\n  \\\"Failed to request input from user for variable var.state_passphrase\\\"\n  \\\"No v\n[…]\nspecific var named + hint + script snippet), missing state passphrase,\nall-missing (every required var listed). preflight is dependency-injected\non the env lookup function so tests stay deterministic.",
          "is_bot": false,
          "headline": "feat(secrets): sync preflight checks required env + emits recovery sn…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T01:58:14Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "bd999123c509a56114a4d80f9f1fbd14e29af99a",
          "body": "cmd/secrets/env previously forced every output value to string at unmarshal\ntime, crashing on lists (vaulter_traefik_cert_paths and similar):\n  json: cannot unmarshal array into Go struct field .value of type string\n\nFix: value is now json.RawMessage. Strings emit as before\n(export TF_VAR_x='value')\n[…]\niteTofuOutputsAsEnv as a testable helper. 5 tests cover:\nmixed value types (string + list + map + bool + number + null),\nsingle-quote escaping, deterministic ordering, empty input, and\nmalformed JSON.",
          "is_bot": false,
          "headline": "fix(secrets): env handles non-string Tofu outputs",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T01:58:14Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "d68575dc2e4b0d3e8f768b967f7bf1c694941837",
          "body": "`git rev-parse HEAD:secrets/all.enc.age` interprets path as git-root-relative\nby default. When called from a subdirectory (e.g. infra-tofu/projects/vaulter\nwhere the archive lives at projects/vaulter/secrets/all.enc.age in git-root\nterms), this fails with \"path exists, but not 'secrets/all.enc.age'\"\n[…]\nession test added: TestDriftFromSubdirectory creates a repo with an\narchive at a nested path and calls HasDrift with the subdirectory as\nrepoPath. Pre-fix: errors out. Post-fix: clean drift detection.",
          "is_bot": false,
          "headline": "fix(git): HasDrift works from subdirectory cwd",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T01:58:14Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ac209b56718c0f1b6e42ec5425acce4711811def",
          "body": "Prior fix (4ec1e1b) used PATCH /envs only, but PATCH returns 404 when\nthe env key doesn't yet exist on the application. New approach:\n- POST /envs first (create); 409 means key already exists\n- On 409, fall back to PATCH /envs (update)\n- Both endpoints require \"is_buildtime\" (not \"is_build_time\")\n\nS\n[…]\nBuildArgs to doBytes error formatting.\n\nResult: SetBuildArgs is now truly idempotent across repeated Tofu\napplies regardless of whether the env key already exists, with\ntype-safe error path detection.",
          "is_bot": false,
          "headline": "fix(coolify): SetBuildArgs uses POST-then-PATCH for idempotent upsert",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-28T01:58:02Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "4ec1e1b2292f2c2c3cf350511b76f776f4ab0427",
          "body": "Probed Coolify v4 (2026-05-26): PATCH /envs/bulk does NOT upsert by key —\nit appends new rows, so repeated runs (Tofu re-applies, CI re-deploys)\nstack up duplicate build args. PATCH /envs (no uuid in path) is upsert\nby key.\n\nAlso: POST/PATCH /envs requires field 'is_buildtime' (not 'is_build_time'\na\n[…]\ndpoint field name inconsistency in\nCoolify v4 — documented in the function doc.\n\nOne HTTP call per build arg now, but catalog is small (~3 per service)\nand idempotency is more important than batching.",
          "is_bot": false,
          "headline": "fix(coolify): SetBuildArgs uses PATCH /envs (upsert) not /envs/bulk",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-26T00:35:16Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "04304a3bd47e91f4cd919c7e8657fd0e102c24f9",
          "body": "Coolify v4 has no dedicated build args field on the Application create body\n(probed: build_args, build_pack_buildargs, docker_build_args,\ndockerfile_target_build_args, buildargs all return 422 'field not allowed').\n\nBuild args in Coolify are stored as env vars with is_build_time=true,\nPATCHed via /a\n[…]\n-PATCH with is_build_time=true\n  - TriggerDeploy(appUUID) — GET /deploy?uuid=...\n\nTests: SetBuildArgs sends correct shape + skips malformed; empty list is no-op;\nTriggerDeploy hits the right endpoint.",
          "is_bot": false,
          "headline": "feat(coolify): add --build-arg flag to deploy-app-git",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-26T00:26:39Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "2c917b72fd42b099737bda2a34be99992ff41a13",
          "body": "Adds wapps coolify deploy-app-git → POST /applications/private-github-app.\nCoolify v4 builds the application from a private GitHub repo on the target\nserver (e.g. vaulter-app-01 native arm64), no GHCR pull needed.\n\nRequired for Phase B pivot — vaulter-api 19 services deployed via Coolify\nGitHub App source build instead of GHA-pre-built image + GHCR pull.",
          "is_bot": false,
          "headline": "feat(coolify): deploy-app-git command for private GitHub source builds",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T23:59:40Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "4ca57af787060da18e6e747ebaf134f29a904a69",
          "body": "Coolify v4 /api/v1/applications returns a top-level JSON array, not the\n{\"data\": [...]} envelope shape that the client assumed. The fallback branch\nreturned nil silently, so import-app emitted 0 imports against real Coolify\neven with the destination.server.uuid fix in v0.3.0.\n\nAdded doRaw + doBytes \n[…]\n and\nregression tests TestListApplications_TopLevelArray /\nTestListApplications_DataEnvelope to lock both paths.\n\nUpdated TestImportApp_ServerUUIDFromDestination to use the real top-level\narray shape.",
          "is_bot": false,
          "headline": "fix(coolify): ListApplications handles top-level JSON array response",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T22:30:44Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "84a556299fad112445ae5ea48f0f53abc291104d",
          "body": "Phase A discovery: Coolify v4 /api/v1/applications response nests server_uuid\nunder destination.server.uuid, but wapps-cli was reading a[\"server_uuid\"]\n(top-level) which is null. Filter --server-uuid emitted 0 imports for any\nvalue. Now correctly navigates the nested path.\n\nAdded regression test TestImportApp_ServerUUIDFromDestination to lock the\ncorrect path.",
          "is_bot": false,
          "headline": "fix(coolify): import-app reads server_uuid from destination.server.uuid",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T22:27:43Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "b7e4343a975bf9be2f6ac9947fe2179f63339f2f",
          "body": "…stubs)",
          "is_bot": false,
          "headline": "feat(coolify): import-app command (list + emit Tofu imports.sh + HCL …",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T19:06:16Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "42b14ee2c17d6109d1052a3ff019ca03fab81d3f",
          "body": "…ands",
          "is_bot": false,
          "headline": "feat(coolify): set-labels (with certresolver strip) + update-env comm…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T19:05:40Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "f7049ff6e4286cc441f3ed87ffb820c55337f19e",
          "body": null,
          "is_bot": false,
          "headline": "feat(coolify): deploy-app command (dockercompose create + start)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T19:05:04Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "db47132084aaf2c2e566997823acb8fc6dd38f10",
          "body": null,
          "is_bot": false,
          "headline": "feat(coolify): REST client with create/patch/start/list primitives",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T19:04:13Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "51c6da5bdd2dae78407d3c7da803728a5ec9cfee",
          "body": "Default homebrew formula directory is repo root, but mixing with README.md\nand other root files prevents 'brew tap' auto-discovery (verified: had to\nmanually mv wapps.rb -> Formula/wapps.rb during v0.1.0 release to make\n'brew install wapps' work). Setting directory: Formula makes future\nreleases (v0.2.0+) push the formula directly to Formula/wapps.rb, no\nmanual intervention needed.",
          "is_bot": false,
          "headline": "ci(goreleaser): brews[].directory = Formula",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T19:01:07Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "f1e2cb25d664aae6fd2a7480079da1c97645c663",
          "body": "GoReleaser v2 default uses GITHUB_TOKEN for SCM ops, but cross-repo formula\npush to wappsdev/homebrew-tap needs a PAT with cross-repo write scope.\nSet brews[0].repository.token = {{ .Env.HOMEBREW_TAP_PAT }} explicitly so\nGoReleaser uses the PAT for the formula push step (the auto GITHUB_TOKEN\nonly has repo scope on wapps-cli itself, hence the previous 403).\n\nAlso pinned the formula commit identity to wapps-release-bot@wapps.co.",
          "is_bot": false,
          "headline": "fix(ci): explicit HOMEBREW_TAP_PAT token in brews repository config",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:55:06Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "fa4107376d8b303392664498c0e9a30b31bc1e69",
          "body": "- .goreleaser.yml: cross-compile linux+darwin × amd64+arm64, archive as\n  tar.gz with versioned names, sha256 checksums, brew formula published to\n  wappsdev/homebrew-tap with assert-help test recipe.\n- release.yml: triggered on v* tags, uses HOMEBREW_TAP_PAT secret for\n  formula push.\n- ci.yml: PR + main push runs vet + race-test + build for fast feedback.\n\nNote: HOMEBREW_TAP_PAT secret must be set before the first v0.1.0 tag push\n(handled by controller; see Phase A plan Task 19 Step 4-5).",
          "is_bot": false,
          "headline": "ci: GoReleaser config + release + CI workflows",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:45:07Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "652554deff47cb99e97b122e020be6520b6ea055",
          "body": "…nt wraps\n\n- internal/git/git.go: error wraps now follow Layer.Method convention\n  (git.HasDrift: fetch / git.Pull: / git.fileSha: ref:file) matching the\n  rest of the codebase (ageutil, secrets, tofu packages).\n- internal/git/git.go: fileSha error suppression narrowed — only swallows\n  'does not ex\n[…]\n\n- cmd/git/status.go: now prints 'not inside a git repository — drift check\n  skipped' instead of leaking raw 'fatal: not a git repository' when run\n  outside a repo (e.g. wapps git status from /tmp).",
          "is_bot": false,
          "headline": "fix(git): narrow fileSha error suppression + IsRepo helper + consiste…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:42:41Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "d38131017b2757f5cf00f79183162181b2744aaf",
          "body": null,
          "is_bot": false,
          "headline": "feat(git): wapps git status command",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:39:21Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "5bb79d98511888144a3a28f64f8cd85b4e56b28a",
          "body": null,
          "is_bot": false,
          "headline": "feat(git): auto-sync preflight (fetch + pull on drift)",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:38:30Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "75536b6d6d6602de2462e15cb500044c9ac64b77",
          "body": null,
          "is_bot": false,
          "headline": "feat(secrets): add env (dump) + rotate-master subcommands",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:37:19Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "ac755297e2cab783ac4b605f76e3fd9fd745fd8e",
          "body": "…d tidy\n\n- doctor.go: handle http.NewRequest error (prevents nil-pointer panic when\n  COOLIFY_URL is malformed); use switch for cleaner err/5xx/ok branches;\n  always close response body via explicit Close before status check.\n- secrets/sync.go: add comment explaining the dateFmt = '+' + '%Y-%m-%d'\n \n[…]\nvet's printf format-string warning while emitting\n  the literal shell snippet $(date +%Y-%m-%d) for the user's shell to expand.\n- go.mod: tidy removed unused viper deps + indirect transitive packages.",
          "is_bot": false,
          "headline": "fix(cli): doctor nil-pointer + sync.go vet workaround comment + go mo…",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:35:24Z",
          "body_truncated": true,
          "is_coding_agent": false
        },
        {
          "oid": "ac3200bda56e6f9cc86dc7f205a486ad75a01e77",
          "body": null,
          "is_bot": false,
          "headline": "feat(secrets): add get/list/verify commands",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:28:54Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "15c8884dd568571afc9b7983efbe8b13fc4ceb31",
          "body": null,
          "is_bot": false,
          "headline": "feat(secrets): wapps secrets sync — tofu output → age archive",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:27:56Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "0bc191f57b9c299dd5177e2d9ff8af8daa8626c8",
          "body": null,
          "is_bot": false,
          "headline": "feat(ageutil): scrypt-based encrypt/decrypt helpers",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:26:08Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "47f132849e8c5ec7abba4cf9430db1cea9797ef0",
          "body": null,
          "is_bot": false,
          "headline": "feat(doctor): end-to-end dependency + access check",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:25:32Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "426dd667e3141630af6790e71334b1d6e2dfea64",
          "body": null,
          "is_bot": false,
          "headline": "feat: cobra root command + global flags",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T18:24:58Z",
          "body_truncated": false,
          "is_coding_agent": false
        },
        {
          "oid": "61b945eba442074665e0d495d2461628154ae693",
          "body": null,
          "is_bot": false,
          "headline": "feat: bootstrap wapps-cli Go module",
          "author_name": "Adnan Kurt",
          "author_login": "adnankurt16",
          "committed_at": "2026-05-25T17:21:16Z",
          "body_truncated": false,
          "is_coding_agent": false
        }
      ],
      "releases_count": 23,
      "commits_last_year": 87,
      "latest_release_at": "2026-07-13T12:33:11Z",
      "latest_release_tag": "v0.19.0",
      "releases_from_tags": false,
      "days_since_last_push": 14,
      "active_weeks_last_year": 7,
      "days_since_latest_release": 14,
      "mean_days_between_releases": 4.4
    },
    "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": "github.com/wappsdev/wapps-cli",
          "exists": true,
          "license": null,
          "keywords": [],
          "ecosystem": "go",
          "matches_repo": true,
          "registry_url": "https://pkg.go.dev/github.com/wappsdev/wapps-cli",
          "is_deprecated": false,
          "latest_version": "v0.19.0",
          "repository_url": "https://github.com/wappsdev/wapps-cli",
          "versions_count": 23,
          "total_downloads": null,
          "dependents_count": null,
          "deprecation_note": null,
          "maintainers_count": null,
          "monthly_downloads": null,
          "first_published_at": null,
          "latest_published_at": "2026-07-13T12:31:55Z",
          "latest_version_yanked": null,
          "days_since_latest_publish": 14
        }
      ]
    },
    "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": [
        "worker/tsconfig.json"
      ],
      "toolchain_manifests": [
        "go.mod"
      ],
      "largest_source_bytes": 35832,
      "source_files_sampled": 199,
      "oversized_source_files": 0,
      "agent_instruction_files": [
        ".cursorrules"
      ],
      "agent_instruction_max_bytes": 1639
    },
    "dependencies": {
      "manifests": [
        "go.mod",
        "worker/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": [
        "go",
        "npm"
      ],
      "dependencies": [
        {
          "name": "filippo.io/age",
          "manifest": "go.mod",
          "ecosystem": "go",
          "version_constraint": "v1.3.1"
        },
        {
          "name": "github.com/spf13/cobra",
          "manifest": "go.mod",
          "ecosystem": "go",
          "version_constraint": "v1.10.2"
        },
        {
          "name": "github.com/stretchr/testify",
          "manifest": "go.mod",
          "ecosystem": "go",
          "version_constraint": "v1.11.1"
        },
        {
          "name": "golang.org/x/crypto",
          "manifest": "go.mod",
          "ecosystem": "go",
          "version_constraint": "v0.45.0"
        },
        {
          "name": "golang.org/x/term",
          "manifest": "go.mod",
          "ecosystem": "go",
          "version_constraint": "v0.37.0"
        },
        {
          "name": "gopkg.in/yaml.v3",
          "manifest": "go.mod",
          "ecosystem": "go",
          "version_constraint": "v3.0.1"
        },
        {
          "name": "@noble/ciphers",
          "manifest": "worker/package.json",
          "ecosystem": "npm",
          "version_constraint": "2.0.1"
        },
        {
          "name": "@noble/hashes",
          "manifest": "worker/package.json",
          "ecosystem": "npm",
          "version_constraint": "^1.8.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": 33,
        "open_issues": 0,
        "closed_ratio": null,
        "closed_issues": 0,
        "closed_unmerged_prs": 1
      },
      "bus_factor": 1,
      "bot_contributors": 0,
      "top_contributors": [
        {
          "type": "User",
          "login": "adnankurt16",
          "commits": 87,
          "avatar_url": "https://avatars.githubusercontent.com/u/8597614?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": [
        "go.sum"
      ],
      "scorecard": {
        "checks": [
          {
            "name": "Binary-Artifacts",
            "score": 10,
            "reason": "no binaries found in the repo",
            "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": 10,
            "reason": "20 out of 20 merged PRs checked by a CI test -- score normalized to 10",
            "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/26 approved changesets -- score normalized to 0",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#code-review"
          },
          {
            "name": "Contributors",
            "score": 3,
            "reason": "project has 1 contributing companies or organizations -- score normalized to 3",
            "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": 0,
            "reason": "project was created within the last 90 days. Please review its contents carefully",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#maintained"
          },
          {
            "name": "Packaging",
            "score": 10,
            "reason": "packaging workflow 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": 0,
            "reason": "Project has not signed or included provenance with any releases.",
            "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": "30 existing vulnerabilities detected",
            "documentation_url": "https://github.com/ossf/scorecard/blob/c395761df6afe1a69e476bc60a013a94bcbc153f/docs/checks.md#vulnerabilities"
          }
        ],
        "commit": "db07ff7e9202b19860ea58cf411672589d122c8c",
        "ran_at": "2026-07-28T05:47:24Z",
        "aggregate_score": 2.7,
        "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-13T13:22:20Z",
      "oldest_open_prs": [],
      "last_merged_pr_at": "2026-07-13T13:02:57Z",
      "ci_last_conclusion": "SUCCESS",
      "oldest_open_issues": []
    }
  },
  "config": {
    "disabled_metrics": [],
    "disabled_categories": [],
    "disabled_components": {}
  },
  "source": {
    "url": "https://github.com/wappsdev/wapps-cli",
    "host": "github.com",
    "name": "wapps-cli",
    "owner": "wappsdev"
  },
  "metrics": {
    "overall": {
      "key": "overall",
      "band": "at_risk",
      "name": "Overall health",
      "note": null,
      "notes": [],
      "value": 49,
      "inputs": {
        "security": 27,
        "vitality": 67,
        "community": 24,
        "governance": 51,
        "engineering": 67
      },
      "components": []
    },
    "categories": [
      {
        "key": "vitality",
        "band": "moderate",
        "name": "Vitality",
        "value": 67,
        "weight": 0.22,
        "metrics": [
          {
            "key": "development_activity",
            "band": "moderate",
            "name": "Development activity",
            "note": null,
            "notes": [],
            "value": 51,
            "inputs": {
              "commits_last_year": 87,
              "human_commit_share": 1,
              "days_since_last_push": 14,
              "active_weeks_last_year": 7
            },
            "components": [
              {
                "key": "push_recency",
                "name": "Push recency",
                "detail": "last push 14 days ago",
                "points": 28.8,
                "status": "partial",
                "details": [
                  {
                    "code": "push_recency",
                    "params": {
                      "days": 14
                    }
                  }
                ],
                "max_points": 36
              },
              {
                "key": "commit_cadence",
                "name": "Commit cadence",
                "detail": "7/52 weeks with commits",
                "points": 4.8,
                "status": "partial",
                "details": [
                  {
                    "code": "commit_cadence_weeks",
                    "params": {
                      "weeks": 7
                    }
                  }
                ],
                "max_points": 36
              },
              {
                "key": "commit_volume",
                "name": "Commit volume",
                "detail": "87 commits in the last year",
                "points": 17.5,
                "status": "partial",
                "details": [
                  {
                    "code": "commits_last_year",
                    "params": {
                      "count": 87
                    }
                  }
                ],
                "max_points": 18
              },
              {
                "key": "openssf_scorecard_maintained",
                "name": "OpenSSF Scorecard: Maintained",
                "detail": "project was created within the last 90 days. Please review its contents carefully",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 10
              }
            ]
          },
          {
            "key": "release_discipline",
            "band": "excellent",
            "name": "Release discipline",
            "note": null,
            "notes": [],
            "value": 90,
            "inputs": {
              "releases_count": 23,
              "latest_release_tag": "v0.19.0",
              "releases_from_tags": false,
              "days_since_latest_release": 14,
              "mean_days_between_releases": 4.4
            },
            "components": [
              {
                "key": "ships_releases",
                "name": "Ships releases",
                "detail": "23 releases published",
                "points": 27,
                "status": "met",
                "details": [
                  {
                    "code": "releases_published",
                    "params": {
                      "count": 23
                    }
                  }
                ],
                "max_points": 27
              },
              {
                "key": "release_recency",
                "name": "Release recency",
                "detail": "latest release 14 days ago",
                "points": 36,
                "status": "met",
                "details": [
                  {
                    "code": "release_recency",
                    "params": {
                      "days": 14
                    }
                  }
                ],
                "max_points": 36
              },
              {
                "key": "release_cadence",
                "name": "Release cadence",
                "detail": "a release every ~4.4 days",
                "points": 27,
                "status": "met",
                "details": [
                  {
                    "code": "release_cadence",
                    "params": {
                      "gap": 4.4
                    }
                  }
                ],
                "max_points": 27
              },
              {
                "key": "openssf_scorecard_signed_releases",
                "name": "OpenSSF Scorecard: Signed-Releases",
                "detail": "Project has not signed or included provenance with any releases.",
                "points": 0,
                "status": "missed",
                "details": [],
                "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": "critical",
        "name": "Community & Adoption",
        "value": 24,
        "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
              }
            ]
          }
        ],
        "description": "Does the project have users, downloads, attention, and a welcoming setup for contributors?"
      },
      {
        "key": "governance",
        "band": "moderate",
        "name": "Sustainability & Governance",
        "value": 51,
        "weight": 0.24,
        "metrics": [
          {
            "key": "maintainer_resilience",
            "band": "critical",
            "name": "Maintainer resilience (bus factor)",
            "note": null,
            "notes": [],
            "value": 13,
            "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 1 contributing companies or organizations -- score normalized to 3",
                "points": 3,
                "status": "partial",
                "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": 33,
              "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": "33/34 decided PRs merged",
                "points": 37.1,
                "status": "partial",
                "details": [
                  {
                    "code": "decided_prs_merged",
                    "params": {
                      "merged": 33,
                      "decided": 34
                    }
                  }
                ],
                "max_points": 38.25
              },
              {
                "key": "openssf_scorecard_code_review",
                "name": "OpenSSF Scorecard: Code-Review",
                "detail": "Found 0/26 approved changesets -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 15
              }
            ]
          },
          {
            "key": "stewardship",
            "band": "at_risk",
            "name": "Ownership & stewardship",
            "note": null,
            "notes": [],
            "value": 39,
            "inputs": {
              "followers": 2,
              "owner_type": "Organization",
              "is_verified": null,
              "owner_login": "wappsdev",
              "public_repos": 3,
              "account_age_days": 194
            },
            "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 wappsdev",
                "points": 3.4,
                "status": "partial",
                "details": [
                  {
                    "code": "owner_followers",
                    "params": {
                      "count": 2,
                      "login": "wappsdev"
                    }
                  }
                ],
                "max_points": 25
              },
              {
                "key": "track_record",
                "name": "Track record",
                "detail": "3 public repos, account ~0 yr old",
                "points": 5.4,
                "status": "partial",
                "details": [
                  {
                    "code": "public_repos",
                    "params": {
                      "count": 3
                    }
                  },
                  {
                    "code": "account_age_years",
                    "params": {
                      "years": 0
                    }
                  }
                ],
                "max_points": 25
              }
            ]
          },
          {
            "key": "package_maintenance",
            "band": "excellent",
            "name": "Package maintenance",
            "note": null,
            "notes": [],
            "value": 100,
            "inputs": {
              "packages": [
                "github.com/wappsdev/wapps-cli"
              ],
              "ecosystems": "go",
              "any_deprecated": false,
              "min_days_since_publish": 14
            },
            "components": [
              {
                "key": "published_resolvable",
                "name": "Published & resolvable",
                "detail": "1 package(s) on go",
                "points": 25,
                "status": "met",
                "details": [
                  {
                    "code": "packages_published",
                    "params": {
                      "count": 1,
                      "ecosystems": "go"
                    }
                  }
                ],
                "max_points": 25
              },
              {
                "key": "publish_recency",
                "name": "Publish recency",
                "detail": "latest publish 14 days ago",
                "points": 35,
                "status": "met",
                "details": [
                  {
                    "code": "publish_recency",
                    "params": {
                      "days": 14
                    }
                  }
                ],
                "max_points": 35
              },
              {
                "key": "version_history",
                "name": "Version history",
                "detail": "23 published versions",
                "points": 20,
                "status": "met",
                "details": [
                  {
                    "code": "published_versions",
                    "params": {
                      "count": 23
                    }
                  }
                ],
                "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": "moderate",
        "name": "Engineering Quality",
        "value": 67,
        "weight": 0.2,
        "metrics": [
          {
            "key": "engineering_practices",
            "band": "moderate",
            "name": "Engineering practices",
            "note": null,
            "notes": [],
            "value": 68,
            "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": "20 out of 20 merged PRs checked by a CI test -- score normalized to 10",
                "points": 20,
                "status": "met",
                "details": [],
                "max_points": 20
              }
            ]
          },
          {
            "key": "documentation",
            "band": "moderate",
            "name": "Documentation",
            "note": null,
            "notes": [],
            "value": 65,
            "inputs": {
              "topics": [],
              "has_wiki": false,
              "homepage": null,
              "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": null,
                "points": 0,
                "status": "missed",
                "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": null,
                "points": 0,
                "status": "missed",
                "details": [],
                "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": "critical",
        "name": "Security",
        "value": 27,
        "weight": 0.16,
        "metrics": [
          {
            "key": "security_posture",
            "band": "critical",
            "name": "Security posture",
            "note": null,
            "notes": [],
            "value": 27,
            "inputs": {
              "source": "openssf_scorecard",
              "checks_evaluated": 18,
              "scorecard_version": "v5.5.0",
              "checks_inconclusive": 0,
              "scorecard_aggregate": 2.7
            },
            "components": [
              {
                "key": "binary_artifacts",
                "name": "Binary-Artifacts",
                "detail": "no binaries found in the repo",
                "points": 7.5,
                "status": "met",
                "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": "20 out of 20 merged PRs checked by a CI test -- score normalized to 10",
                "points": 2.5,
                "status": "met",
                "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/26 approved changesets -- score normalized to 0",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "contributors",
                "name": "Contributors",
                "detail": "project has 1 contributing companies or organizations -- score normalized to 3",
                "points": 0.8,
                "status": "partial",
                "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": "project was created within the last 90 days. Please review its contents carefully",
                "points": 0,
                "status": "missed",
                "details": [],
                "max_points": 7.5
              },
              {
                "key": "packaging",
                "name": "Packaging",
                "detail": "packaging workflow detected",
                "points": 5,
                "status": "met",
                "details": [],
                "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": "Project has not signed or included provenance with any releases.",
                "points": 0,
                "status": "missed",
                "details": [],
                "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": "30 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": 74,
        "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": [
                ".cursorrules"
              ],
              "agent_instruction_max_bytes": 1639
            },
            "components": [
              {
                "key": "agent_instructions",
                "name": "Agent instructions",
                "detail": ".cursorrules",
                "points": 45,
                "status": "met",
                "details": [
                  {
                    "code": "file_list",
                    "params": {
                      "files": ".cursorrules"
                    }
                  }
                ],
                "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": "87 of 87 human commits state their intent (structured subject or explanatory body)",
                "points": 40,
                "status": "met",
                "details": [
                  {
                    "code": "legible_history",
                    "params": {
                      "legible": 87,
                      "sampled": 87
                    }
                  }
                ],
                "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": [
                "go.sum"
              ],
              "has_dockerfile": false,
              "typed_language": true,
              "bootstrap_files": [],
              "has_devcontainer": false,
              "has_linter_config": false,
              "typecheck_configs": [
                "worker/tsconfig.json"
              ],
              "agent_commit_share": 0,
              "toolchain_manifests": [
                "go.mod"
              ],
              "dependency_bot_commit_share": 0
            },
            "components": [
              {
                "key": "one_command_bootstrap",
                "name": "One-command bootstrap",
                "detail": "go.mod (toolchain convention, no task runner)",
                "points": 12.6,
                "status": "partial",
                "details": [
                  {
                    "code": "toolchain_convention",
                    "params": {
                      "files": "go.mod"
                    }
                  }
                ],
                "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": "worker/tsconfig.json",
                "points": 11,
                "status": "met",
                "details": [
                  {
                    "code": "file_list",
                    "params": {
                      "files": "worker/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 87",
                "points": 0,
                "status": "missed",
                "details": [
                  {
                    "code": "no_agent_authored_commits",
                    "params": {
                      "sampled": 87
                    }
                  }
                ],
                "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": "excellent",
            "name": "Code legibility for models",
            "note": null,
            "notes": [],
            "value": 100,
            "inputs": {
              "primary_language": "Go",
              "largest_source_bytes": 35832,
              "source_files_sampled": 199,
              "oversized_source_files": 0
            },
            "components": [
              {
                "key": "type_checkable_code",
                "name": "Type-checkable code",
                "detail": "Go (statically typed)",
                "points": 45,
                "status": "met",
                "details": [
                  {
                    "code": "statically_typed_language",
                    "params": {
                      "language": "Go"
                    }
                  }
                ],
                "max_points": 45
              },
              {
                "key": "manageable_file_sizes",
                "name": "Manageable file sizes",
                "detail": "0/199 source files over 60KB",
                "points": 55,
                "status": "met",
                "details": [
                  {
                    "code": "oversized_source_files",
                    "params": {
                      "kb": 60,
                      "sampled": 199,
                      "oversized": 0
                    }
                  }
                ],
                "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": [
    "GitHub dependency-graph SBOM unavailable (404); the dependency graph may be disabled for this repository"
  ],
  "report_type": "repository",
  "generated_at": "2026-07-28T05:47:39.095947Z",
  "schema_version": "0.27.0",
  "badge_url": "https://raw.githubusercontent.com/inspect-software/badges/main/v1/w/wappsdev/wapps-cli.svg",
  "full_name": "wappsdev/wapps-cli",
  "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 agregadasGo.