Workspaces Payload collection with the PAT as a write-only field: access.read () => false strips it from every access-controlled read path, and a field-level beforeChange hook encrypts on write with AES-256-GCM (scrypt key from VEECT_SECRET, random per-value salt + IV, v1 storage format) via node:crypto only. The real repository replaces the phase-1 stub with payload create/findByID; toDomain never maps the credential, and getDecryptedCredential(id) is the single server-side decrypt path for the runner handoff (story 07). Contract suite now covers create, write-only behaviour, and the decrypt path against both the mock and the Payload impl (stub runs the real collection hooks). Missing VEECT_SECRET fails production bind/boot with an actionable message; dev-seed boots without it. Env declared in turbo.json globalEnv + .env.example. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016j8z4VHjedXDTjEDNg7qHK
104 lines
2.2 KiB
JSON
104 lines
2.2 KiB
JSON
{
|
|
"$schema": "https://turborepo.dev/schema.json",
|
|
"globalDependencies": [".env"],
|
|
"globalEnv": [
|
|
"CI",
|
|
"DATABASE_URL",
|
|
"PAYLOAD_SECRET",
|
|
"NODE_ENV",
|
|
"USE_DEV_SEED",
|
|
"WEB_NEXT_SENTRY_DSN",
|
|
"NEXT_PUBLIC_WEB_NEXT_SENTRY_DSN",
|
|
"CMS_SENTRY_DSN",
|
|
"SENTRY_AUTH_TOKEN",
|
|
"SENTRY_ORG",
|
|
"SENTRY_PROJECT_WEB_NEXT",
|
|
"SENTRY_PROJECT_CMS",
|
|
"SENTRY_TRACES_SAMPLE_RATE",
|
|
"SENTRY_ENVIRONMENT",
|
|
"VERCEL_GIT_COMMIT_SHA",
|
|
"NEXT_PUBLIC_VERCEL_GIT_COMMIT_SHA",
|
|
"VERCEL_ENV",
|
|
"AUDIT_PSEUDONYM_SALT",
|
|
"VEECT_SECRET"
|
|
],
|
|
"boundaries": {
|
|
"tags": {
|
|
"app": {
|
|
"dependencies": {
|
|
"allow": ["app", "core", "core-composition", "feature", "tooling"]
|
|
}
|
|
},
|
|
"feature": {
|
|
"dependencies": {
|
|
"allow": ["core", "feature", "tooling"]
|
|
}
|
|
},
|
|
"core": {
|
|
"dependencies": {
|
|
"allow": ["core", "core-composition", "tooling"]
|
|
}
|
|
},
|
|
"core-composition": {
|
|
"dependencies": {
|
|
"allow": ["core", "core-composition", "feature", "tooling"]
|
|
}
|
|
},
|
|
"tooling": {
|
|
"dependencies": {
|
|
"allow": ["tooling"]
|
|
}
|
|
}
|
|
}
|
|
},
|
|
"tasks": {
|
|
"build": {
|
|
"dependsOn": ["^build"],
|
|
"outputs": ["dist/**", ".next/**", "!.next/cache/**"]
|
|
},
|
|
"dev": {
|
|
"cache": false,
|
|
"persistent": true
|
|
},
|
|
"lint": {
|
|
"dependsOn": ["^lint"]
|
|
},
|
|
"test": {
|
|
"dependsOn": []
|
|
},
|
|
"test:e2e": {
|
|
"dependsOn": ["^build"],
|
|
"cache": false
|
|
},
|
|
"typecheck": {
|
|
"dependsOn": []
|
|
},
|
|
"conformance": {
|
|
"inputs": [
|
|
"packages/*/src/feature.manifest.ts",
|
|
"scripts/conformance.mjs",
|
|
"packages/core-eslint/rules/_manifest-ast.js"
|
|
],
|
|
"outputs": []
|
|
},
|
|
"fallow": {
|
|
"inputs": [
|
|
"packages/**/src/**/*.ts",
|
|
"packages/**/src/**/*.tsx",
|
|
"apps/**/src/**/*.ts",
|
|
"apps/**/src/**/*.tsx",
|
|
"scripts/**/*.mjs",
|
|
".fallowrc.json"
|
|
],
|
|
"outputs": []
|
|
},
|
|
"build-storybook": {
|
|
"outputs": ["storybook-static/**"]
|
|
},
|
|
"test:stories": {
|
|
"dependsOn": ["build-storybook"],
|
|
"cache": false
|
|
}
|
|
}
|
|
}
|