mustflow 2.38.0 → 2.58.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -0
- package/dist/cli/commands/run/executor.js +16 -0
- package/dist/cli/commands/run/process-tree.js +6 -3
- package/dist/cli/commands/verify.js +3 -1
- package/dist/cli/lib/git-changes.js +11 -1
- package/dist/cli/lib/i18n.js +1 -1
- package/dist/cli/lib/local-index/index.js +8 -4
- package/dist/cli/lib/local-index/populate.js +17 -3
- package/dist/cli/lib/local-index/search-read-model.js +9 -7
- package/dist/cli/lib/local-index/search-text.js +2 -2
- package/dist/cli/lib/local-index/workflow-documents.js +17 -2
- package/dist/cli/lib/mustflow-read.js +14 -2
- package/dist/cli/lib/repo-map.js +16 -3
- package/dist/cli/lib/templates.js +8 -7
- package/dist/cli/lib/validation/constants.js +1 -1
- package/dist/core/active-run-locks.js +78 -20
- package/dist/core/change-classification.js +4 -0
- package/dist/core/command-contract-rules.js +1 -1
- package/dist/core/command-contract-validation.js +1 -1
- package/dist/core/command-cwd.js +13 -2
- package/dist/core/command-effects.js +22 -4
- package/dist/core/command-env.js +8 -6
- package/dist/core/command-preconditions.js +28 -2
- package/dist/core/completion-verdict.js +1 -1
- package/dist/core/line-endings.js +8 -4
- package/dist/core/safe-filesystem.js +9 -1
- package/dist/core/source-anchor-validation.js +7 -1
- package/dist/core/source-anchors.js +8 -2
- package/dist/core/verification-scheduler.js +8 -2
- package/package.json +1 -1
- package/templates/default/common/.mustflow/config/commands.toml +39 -15
- package/templates/default/i18n.toml +330 -1
- package/templates/default/locales/en/.mustflow/skills/INDEX.md +302 -5
- package/templates/default/locales/en/.mustflow/skills/agent-eval-integrity-review/SKILL.md +160 -0
- package/templates/default/locales/en/.mustflow/skills/agent-execution-control-review/SKILL.md +163 -0
- package/templates/default/locales/en/.mustflow/skills/ai-generated-code-hardening/SKILL.md +49 -13
- package/templates/default/locales/en/.mustflow/skills/api-access-control-review/SKILL.md +298 -0
- package/templates/default/locales/en/.mustflow/skills/api-misuse-resistance-review/SKILL.md +297 -0
- package/templates/default/locales/en/.mustflow/skills/api-request-performance-review/SKILL.md +189 -0
- package/templates/default/locales/en/.mustflow/skills/app-startup-performance-review/SKILL.md +309 -0
- package/templates/default/locales/en/.mustflow/skills/backend-log-evidence-review/SKILL.md +213 -0
- package/templates/default/locales/en/.mustflow/skills/business-rule-leakage-review/SKILL.md +295 -0
- package/templates/default/locales/en/.mustflow/skills/cache-integrity-review/SKILL.md +291 -0
- package/templates/default/locales/en/.mustflow/skills/change-blast-radius-review/SKILL.md +297 -0
- package/templates/default/locales/en/.mustflow/skills/client-bundle-pruning-review/SKILL.md +160 -0
- package/templates/default/locales/en/.mustflow/skills/cloud-cost-guardrail-review/SKILL.md +321 -0
- package/templates/default/locales/en/.mustflow/skills/concurrency-invariant-review/SKILL.md +193 -0
- package/templates/default/locales/en/.mustflow/skills/core-web-vitals-field-review/SKILL.md +161 -0
- package/templates/default/locales/en/.mustflow/skills/credit-ledger-integrity-review/SKILL.md +156 -0
- package/templates/default/locales/en/.mustflow/skills/database-json-modeling-review/SKILL.md +171 -0
- package/templates/default/locales/en/.mustflow/skills/database-lock-contention-review/SKILL.md +192 -0
- package/templates/default/locales/en/.mustflow/skills/database-migration-change/SKILL.md +76 -34
- package/templates/default/locales/en/.mustflow/skills/database-query-bottleneck-review/SKILL.md +194 -0
- package/templates/default/locales/en/.mustflow/skills/deletion-lifecycle-review/SKILL.md +171 -0
- package/templates/default/locales/en/.mustflow/skills/deployment-rollout-safety-review/SKILL.md +321 -0
- package/templates/default/locales/en/.mustflow/skills/desktop-auto-update-safety-review/SKILL.md +265 -0
- package/templates/default/locales/en/.mustflow/skills/desktop-background-process-stability-review/SKILL.md +318 -0
- package/templates/default/locales/en/.mustflow/skills/desktop-memory-footprint-review/SKILL.md +318 -0
- package/templates/default/locales/en/.mustflow/skills/error-message-integrity-review/SKILL.md +283 -0
- package/templates/default/locales/en/.mustflow/skills/failure-integrity-review/SKILL.md +193 -0
- package/templates/default/locales/en/.mustflow/skills/file-upload-security-review/SKILL.md +305 -0
- package/templates/default/locales/en/.mustflow/skills/frame-render-performance-review/SKILL.md +159 -0
- package/templates/default/locales/en/.mustflow/skills/frontend-accessibility-tree-review/SKILL.md +202 -0
- package/templates/default/locales/en/.mustflow/skills/frontend-localization-review/SKILL.md +202 -0
- package/templates/default/locales/en/.mustflow/skills/frontend-state-ownership-review/SKILL.md +183 -0
- package/templates/default/locales/en/.mustflow/skills/frontend-stress-layout-review/SKILL.md +193 -0
- package/templates/default/locales/en/.mustflow/skills/hot-path-performance-review/SKILL.md +159 -0
- package/templates/default/locales/en/.mustflow/skills/idempotency-integrity-review/SKILL.md +195 -0
- package/templates/default/locales/en/.mustflow/skills/image-delivery-performance-review/SKILL.md +161 -0
- package/templates/default/locales/en/.mustflow/skills/incident-triage-review/SKILL.md +185 -0
- package/templates/default/locales/en/.mustflow/skills/llm-hallucination-control-review/SKILL.md +155 -0
- package/templates/default/locales/en/.mustflow/skills/llm-response-latency-review/SKILL.md +155 -0
- package/templates/default/locales/en/.mustflow/skills/llm-service-ux-review/SKILL.md +2 -0
- package/templates/default/locales/en/.mustflow/skills/llm-token-cost-control-review/SKILL.md +155 -0
- package/templates/default/locales/en/.mustflow/skills/low-end-device-support-review/SKILL.md +340 -0
- package/templates/default/locales/en/.mustflow/skills/memory-lifetime-review/SKILL.md +169 -0
- package/templates/default/locales/en/.mustflow/skills/mobile-energy-efficiency-review/SKILL.md +329 -0
- package/templates/default/locales/en/.mustflow/skills/module-boundary-review/SKILL.md +278 -0
- package/templates/default/locales/en/.mustflow/skills/multi-agent-work-coordination/SKILL.md +1 -0
- package/templates/default/locales/en/.mustflow/skills/observability-debuggability-review/SKILL.md +208 -0
- package/templates/default/locales/en/.mustflow/skills/payment-integrity-review/SKILL.md +155 -0
- package/templates/default/locales/en/.mustflow/skills/prompt-contract-quality-review/SKILL.md +158 -0
- package/templates/default/locales/en/.mustflow/skills/quadratic-scan-review/SKILL.md +155 -0
- package/templates/default/locales/en/.mustflow/skills/queue-processing-integrity-review/SKILL.md +193 -0
- package/templates/default/locales/en/.mustflow/skills/race-condition-review/SKILL.md +188 -0
- package/templates/default/locales/en/.mustflow/skills/rate-limit-integrity-review/SKILL.md +344 -0
- package/templates/default/locales/en/.mustflow/skills/retry-policy-integrity-review/SKILL.md +195 -0
- package/templates/default/locales/en/.mustflow/skills/routes.toml +330 -0
- package/templates/default/locales/en/.mustflow/skills/security-flow-review/SKILL.md +279 -0
- package/templates/default/locales/en/.mustflow/skills/testability-boundary-review/SKILL.md +295 -0
- package/templates/default/locales/en/.mustflow/skills/transaction-boundary-integrity-review/SKILL.md +196 -0
- package/templates/default/locales/en/.mustflow/skills/type-state-modeling-review/SKILL.md +179 -0
- package/templates/default/locales/en/.mustflow/skills/web-render-performance-review/SKILL.md +164 -0
- package/templates/default/manifest.toml +388 -2
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
---
|
|
2
|
+
mustflow_doc: skill.database-json-modeling-review
|
|
3
|
+
locale: en
|
|
4
|
+
canonical: true
|
|
5
|
+
revision: 1
|
|
6
|
+
lifecycle: mustflow-owned
|
|
7
|
+
authority: procedure
|
|
8
|
+
name: database-json-modeling-review
|
|
9
|
+
description: Apply this skill when code, schema, migrations, repositories, ORM models, SQL, docs, tests, or reviews introduce, change, or assess database JSON, jsonb, metadata, extra, options, settings, attributes, properties, raw payload, event context, dynamic field, generated column, computed column, expression index, JSON search index, JSON path query, schemaVersion, JSON key registry, or JSON-to-column promotion behavior.
|
|
10
|
+
metadata:
|
|
11
|
+
mustflow_schema: "1"
|
|
12
|
+
mustflow_kind: procedure
|
|
13
|
+
pack_id: mustflow.core
|
|
14
|
+
skill_id: mustflow.core.database-json-modeling-review
|
|
15
|
+
command_intents:
|
|
16
|
+
- changes_status
|
|
17
|
+
- changes_diff_summary
|
|
18
|
+
- test_related
|
|
19
|
+
- test
|
|
20
|
+
- lint
|
|
21
|
+
- build
|
|
22
|
+
- docs_validate_fast
|
|
23
|
+
- test_release
|
|
24
|
+
- mustflow_check
|
|
25
|
+
---
|
|
26
|
+
|
|
27
|
+
# Database JSON Modeling Review
|
|
28
|
+
|
|
29
|
+
<!-- mustflow-section: purpose -->
|
|
30
|
+
## Purpose
|
|
31
|
+
|
|
32
|
+
Keep JSON columns from becoming a place where schema, ownership, validation, indexing, retention, and product decisions disappear.
|
|
33
|
+
|
|
34
|
+
The review question is: "Is this value truly document-shaped context, or is it a real domain field pretending to be flexible?" JSON is acceptable for bounded optional context, raw external evidence, event-specific details, rare settings, or payloads that are inspected by humans. A key that drives filters, ordering, joins, permissions, uniqueness, status, dates, money, tenant scope, deletion, audit, or calculations is no longer harmless metadata.
|
|
35
|
+
|
|
36
|
+
<!-- mustflow-section: use-when -->
|
|
37
|
+
## Use When
|
|
38
|
+
|
|
39
|
+
- A database column, ORM field, migration, fixture, repository, query, generated client, seed, or docs surface uses `JSON`, `jsonb`, `json`, `metadata`, `extra`, `options`, `settings`, `attributes`, `properties`, `payload`, `raw_payload`, `context`, `details`, or similar flexible fields.
|
|
40
|
+
- Code filters, sorts, groups, joins, aggregates, validates, authorizes, displays, exports, deletes, audits, or backfills data inside a JSON column.
|
|
41
|
+
- A JSON key might become a status, tenant key, permission bit, date, numeric value, money amount, uniqueness rule, foreign key, lifecycle state, search dimension, reporting dimension, or retention trigger.
|
|
42
|
+
- A raw provider payload, webhook body, import row, API response, analytics event, audit detail, or event context is persisted and might be confused with operational truth.
|
|
43
|
+
- A migration, review, or performance claim mentions generated columns, computed columns, expression indexes, GIN indexes, `jsonb_path_ops`, JSON search indexes, `JSON_VALUE`, `JSON_EXTRACT`, `ISJSON`, check constraints, schema versions, or key registries.
|
|
44
|
+
- A JSON blob holds arrays of objects, mutable and immutable data together, multiple domains, unbounded maps, user-defined keys, or values owned by different teams or services.
|
|
45
|
+
|
|
46
|
+
<!-- mustflow-section: do-not-use-when -->
|
|
47
|
+
## Do Not Use When
|
|
48
|
+
|
|
49
|
+
- The task only changes public API JSON, CLI JSON output, config files, serialization, parsing, or TypeScript object shapes with no database persistence; use the relevant API, CLI, config, or type skill.
|
|
50
|
+
- The task is only database query latency, plan shape, N+1, pagination, or index-fit review; use `database-query-bottleneck-review` first and this skill only when JSON keys hide schema decisions.
|
|
51
|
+
- The task is only migration rollout, online DDL, backfill safety, old/new code compatibility, or destructive schema change; use `database-migration-change` first and this skill as an adjunct for JSON field promotion or shape changes.
|
|
52
|
+
- The task is generic persistence ownership with no flexible JSON column, JSON path, or raw payload surface; use `database-change-safety`.
|
|
53
|
+
- The JSON is a small, bounded, never-queried fixture literal or test-only object whose shape is not persisted or exposed as product behavior.
|
|
54
|
+
|
|
55
|
+
<!-- mustflow-section: required-inputs -->
|
|
56
|
+
## Required Inputs
|
|
57
|
+
|
|
58
|
+
- JSON column role: raw external payload, optional context, event details, rare settings, dynamic attributes, cache snapshot, API projection, audit diff, or operational state.
|
|
59
|
+
- Database engine and feature set when known: PostgreSQL `jsonb` versus `json`, MySQL generated columns, SQL Server computed columns and `ISJSON`, Oracle JSON search indexes, SQLite JSON functions, ORM support, and migration tooling.
|
|
60
|
+
- Key inventory: allowed keys, value types, null policy, default policy, units, precision, timezone or date-only policy, owner, reader, writer, removal policy, and schema version.
|
|
61
|
+
- Query and behavior paths: JSON keys used in `WHERE`, `ORDER BY`, `GROUP BY`, joins, foreign keys, uniqueness, status transitions, permissions, tenant scope, retention, deletion, audit, reporting, search, or calculations.
|
|
62
|
+
- Raw versus operational truth split: which fields are copied into typed columns or child tables, which payload remains immutable evidence, and how drift is reconciled.
|
|
63
|
+
- Cardinality and shape: scalar values, bounded arrays, unbounded arrays, arrays of objects, free-form maps, nested objects, per-domain subdocuments, and expected growth.
|
|
64
|
+
- Migration and compatibility expectations: existing rows, missing keys, old writers, new readers, backfill, dual-write, validation, rollback or roll-forward, generated/computed column deployment, index creation, and cleanup.
|
|
65
|
+
- Tests, fixtures, docs, and configured command-intent contract entries relevant to schema, query, migration, release, and mustflow validation.
|
|
66
|
+
|
|
67
|
+
<!-- mustflow-section: preconditions -->
|
|
68
|
+
## Preconditions
|
|
69
|
+
|
|
70
|
+
- The task matches the Use When conditions and does not match the Do Not Use When exclusions.
|
|
71
|
+
- Required inputs are available, or missing JSON role, key ownership, engine, workload, or migration evidence can be reported without guessing.
|
|
72
|
+
- Higher-priority instructions and `.mustflow/config/commands.toml` have been checked for the current scope.
|
|
73
|
+
- If JSON keys affect authorization, personal data, secrets, retention, audit, tenant scope, or provider payloads, also use the relevant security, privacy, or adapter-boundary skill.
|
|
74
|
+
- If JSON key promotion changes old/new schema compatibility, also use `database-migration-change`.
|
|
75
|
+
- If JSON path predicates, indexes, generated columns, or planner claims are made, also use the matching database engine skill or `database-query-bottleneck-review` before claiming runtime behavior.
|
|
76
|
+
|
|
77
|
+
<!-- mustflow-section: allowed-edits -->
|
|
78
|
+
## Allowed Edits
|
|
79
|
+
|
|
80
|
+
- Add or change schema, migrations, ORM models, generated/computed columns, check constraints, JSON key validation, child tables, indexes, repositories, tests, fixtures, docs, and directly synchronized template surfaces tied to the task.
|
|
81
|
+
- Promote JSON keys into typed columns or child tables when they drive query, integrity, lifecycle, authorization, reporting, or high-volume behavior.
|
|
82
|
+
- Preserve raw external payloads separately from operational columns when evidence or replay value is needed.
|
|
83
|
+
- Add key registries, schema versions, owner documentation, and promotion criteria where flexible fields remain.
|
|
84
|
+
- Do not treat "flexibility" as sufficient justification for storing business state in a JSON blob.
|
|
85
|
+
- Do not add engine-specific JSON indexes, generated columns, computed columns, or search indexes without naming the query shape, write cost, migration path, and engine support boundary.
|
|
86
|
+
|
|
87
|
+
<!-- mustflow-section: procedure -->
|
|
88
|
+
## Procedure
|
|
89
|
+
|
|
90
|
+
1. Classify the JSON column role.
|
|
91
|
+
- Raw evidence: provider payload, webhook body, import row, API response, or audit before/after detail. Keep immutable where possible and copy operational facts into typed fields.
|
|
92
|
+
- Optional context: bounded details that are displayed or logged but do not control product behavior.
|
|
93
|
+
- Rare settings: low-cardinality, low-query settings that have owners, defaults, validation, and a migration path.
|
|
94
|
+
- Dynamic attributes: customer-defined or integration-defined values. Keep query and authorization promises explicit before accepting the shape.
|
|
95
|
+
- Cache or projection: rebuildable data. State the source of truth and invalidation path.
|
|
96
|
+
2. Run the promotion test for every JSON key mentioned by the diff.
|
|
97
|
+
Promote or duplicate into typed schema when a key is used for:
|
|
98
|
+
- `WHERE`, `ORDER BY`, `GROUP BY`, joins, foreign keys, uniqueness, search ranking, or report grouping.
|
|
99
|
+
- Status, workflow, permission, entitlement, tenant scope, ownership, visibility, delete lifecycle, retention, or audit policy.
|
|
100
|
+
- Numeric calculations, money, quota, inventory, dates, timestamps, timezones, durations, or service-level objectives.
|
|
101
|
+
- High-volume access, concurrency control, idempotency, retry state, reconciliation, or operator dashboards.
|
|
102
|
+
3. Separate raw payload from operational truth.
|
|
103
|
+
- Store provider or event payloads as evidence, not as the only current state.
|
|
104
|
+
- Copy stable provider identifiers, event ids, status, amounts, timestamps, tenant ids, and reconciliation cursors into typed fields when code depends on them.
|
|
105
|
+
- Never require future maintainers to remember which nested path is the real customer status, permission bit, or deletion marker.
|
|
106
|
+
4. Check shape and cardinality.
|
|
107
|
+
- Scalars may stay in JSON only when they are not behavior-driving and remain validated.
|
|
108
|
+
- Bounded arrays of simple values need a documented maximum and duplicate/null policy.
|
|
109
|
+
- Arrays of objects usually want child tables when they need filtering, joining, ordering, uniqueness, independent updates, audit, or growth.
|
|
110
|
+
- Unbounded maps need ownership, key namespace rules, quotas, validation, and export semantics.
|
|
111
|
+
- Split mutable data from static evidence so updates do not rewrite large raw payloads or blur audit history.
|
|
112
|
+
- Split unrelated domains. Payment details, UI preferences, AI policy state, security flags, and provider payloads do not belong in one shared `metadata` blob.
|
|
113
|
+
5. Define the JSON contract if JSON remains.
|
|
114
|
+
- Document allowed keys, type, unit, default, nullability, owner, reader, writer, retention, deletion, and deprecation policy.
|
|
115
|
+
- Add `schemaVersion` or an equivalent version field when shape can evolve.
|
|
116
|
+
- Add validation at the database, model, or write-boundary level. Application-only comments are not a contract.
|
|
117
|
+
- Keep unknown-key behavior explicit: reject, ignore, preserve, namespace, or quarantine.
|
|
118
|
+
6. Review engine-specific storage and indexing.
|
|
119
|
+
- PostgreSQL: prefer `jsonb` for queryable JSON, use ordinary columns for hot keys, use expression indexes for scalar paths, choose GIN only for containment/search shapes, and check whether `jsonb_path_ops` fits containment at the cost of operator coverage.
|
|
120
|
+
- MySQL: use generated columns for indexed JSON paths, keep path expressions stable, and verify type/collation casts before claiming index use.
|
|
121
|
+
- SQL Server: use `ISJSON` checks where appropriate, computed columns for indexed JSON values, and `JSON_VALUE`/`OPENJSON` paths with explicit type and length behavior.
|
|
122
|
+
- Oracle: distinguish function-based indexes for known scalar paths from JSON search indexes for broader document search, and document which query class each supports.
|
|
123
|
+
- SQLite: JSON functions are not a schema substitute; expression indexes and generated columns need version and runtime support checks.
|
|
124
|
+
7. Check integrity, migrations, and compatibility.
|
|
125
|
+
- Backfill promoted columns from JSON with missing-key, malformed-value, duplicate, timezone, precision, and default handling.
|
|
126
|
+
- Keep old and new app versions compatible when rolling deploys can read or write both shapes.
|
|
127
|
+
- Decide whether JSON remains as raw evidence, becomes derived cache, or is removed after promotion.
|
|
128
|
+
- Add constraints and tests for typed promoted values, not only JSON parser success.
|
|
129
|
+
8. Check observability and operations.
|
|
130
|
+
- Add visibility for malformed JSON, unknown keys, rejected keys, backfill counts, promoted-field drift, and JSON path query latency when the repository has such patterns.
|
|
131
|
+
- Make operator-facing docs and dashboards use typed fields for operational truth instead of nested-path folklore.
|
|
132
|
+
|
|
133
|
+
<!-- mustflow-section: postconditions -->
|
|
134
|
+
## Postconditions
|
|
135
|
+
|
|
136
|
+
- JSON column role, key ownership, allowed shape, schema version, and raw-versus-operational split are explicit.
|
|
137
|
+
- Behavior-driving JSON keys are promoted, duplicated into typed fields, or reported with a clear reason they remain JSON.
|
|
138
|
+
- Engine-specific JSON indexing, generated/computed columns, validation, and migration claims are tied to evidence or marked unverified.
|
|
139
|
+
- Existing rows, old/new writers, backfill, validation, rollback or roll-forward, and cleanup expectations are addressed.
|
|
140
|
+
- Remaining JSON modeling risk is named instead of hidden under "flexibility".
|
|
141
|
+
|
|
142
|
+
<!-- mustflow-section: verification -->
|
|
143
|
+
## Verification
|
|
144
|
+
|
|
145
|
+
- Run the narrowest configured tests covering schema, repository, migration, query, validation, fixtures, docs, and template packaging changed by the task.
|
|
146
|
+
- Prefer assertions that prove promoted columns, child tables, key validation, schema versions, malformed-value handling, old-shape compatibility, and raw payload preservation.
|
|
147
|
+
- Use configured docs and release checks when skill text, routes, templates, package metadata, or user-facing docs change.
|
|
148
|
+
- If live database plans or provider payload samples are unavailable, report static-review evidence level rather than claiming production safety.
|
|
149
|
+
|
|
150
|
+
<!-- mustflow-section: failure-handling -->
|
|
151
|
+
## Failure Handling
|
|
152
|
+
|
|
153
|
+
- If the engine or ORM feature support is unknown, stop at the modeling recommendation and report the engine-specific verification gap.
|
|
154
|
+
- If promotion would require destructive or long-running migration work, report the expand/backfill/contract path instead of collapsing it into one step.
|
|
155
|
+
- If a JSON blob is intentionally flexible for customer-defined fields, require namespace, quotas, validation, export, and query promises before accepting it.
|
|
156
|
+
- If a configured test or build fails, preserve the failing intent and output tail, then fix only the JSON modeling contract or synchronized surface exercised by the failure.
|
|
157
|
+
|
|
158
|
+
<!-- mustflow-section: output-format -->
|
|
159
|
+
## Output Format
|
|
160
|
+
|
|
161
|
+
Report:
|
|
162
|
+
|
|
163
|
+
- JSON surface reviewed
|
|
164
|
+
- JSON role and key inventory
|
|
165
|
+
- Promotion decisions: typed column, child table, generated/computed column, expression index, JSON index, raw evidence, or remain JSON
|
|
166
|
+
- Raw payload versus operational truth split
|
|
167
|
+
- Engine-specific storage, validation, and index notes
|
|
168
|
+
- Migration, backfill, compatibility, and cleanup status
|
|
169
|
+
- Tests and command intents run
|
|
170
|
+
- Evidence level: static diff risk, configured-test evidence, engine-feature evidence, plan evidence, production evidence, manual-only, missing, or not applicable
|
|
171
|
+
- Remaining JSON modeling risk
|
package/templates/default/locales/en/.mustflow/skills/database-lock-contention-review/SKILL.md
ADDED
|
@@ -0,0 +1,192 @@
|
|
|
1
|
+
---
|
|
2
|
+
mustflow_doc: skill.database-lock-contention-review
|
|
3
|
+
locale: en
|
|
4
|
+
canonical: true
|
|
5
|
+
revision: 1
|
|
6
|
+
lifecycle: mustflow-owned
|
|
7
|
+
authority: procedure
|
|
8
|
+
name: database-lock-contention-review
|
|
9
|
+
description: Apply this skill when code is created, changed, reviewed, or reported and database lock contention, hot rows, deadlocks, lock waits, row locks, gap or next-key locks, metadata locks, DDL locks, `SELECT ... FOR UPDATE`, `SKIP LOCKED`, optimistic locking, conditional updates, queue table claiming, counter caches, stock or balance updates, long transactions, lock timeouts, idle-in-transaction sessions, or lock observability can make database-backed work block, serialize, deadlock, or overload under concurrent traffic.
|
|
10
|
+
metadata:
|
|
11
|
+
mustflow_schema: "1"
|
|
12
|
+
mustflow_kind: procedure
|
|
13
|
+
pack_id: mustflow.core
|
|
14
|
+
skill_id: mustflow.core.database-lock-contention-review
|
|
15
|
+
command_intents:
|
|
16
|
+
- changes_status
|
|
17
|
+
- changes_diff_summary
|
|
18
|
+
- lint
|
|
19
|
+
- build
|
|
20
|
+
- test_related
|
|
21
|
+
- test
|
|
22
|
+
- docs_validate_fast
|
|
23
|
+
- test_release
|
|
24
|
+
- mustflow_check
|
|
25
|
+
---
|
|
26
|
+
|
|
27
|
+
# Database Lock Contention Review
|
|
28
|
+
|
|
29
|
+
<!-- mustflow-section: purpose -->
|
|
30
|
+
## Purpose
|
|
31
|
+
|
|
32
|
+
Review database-backed write paths by asking whether traffic is forced through the same row, range, index prefix, metadata lock, queue head, or long transaction.
|
|
33
|
+
|
|
34
|
+
The review question is not "is the database slow?" It is "which shared database resource are concurrent requests waiting on, and can the data shape, lock strength, lock order, transaction width, retry policy, and observability make that wait bounded and intentional?"
|
|
35
|
+
|
|
36
|
+
<!-- mustflow-section: use-when -->
|
|
37
|
+
## Use When
|
|
38
|
+
|
|
39
|
+
- Code creates, changes, reviews, or reports a database write path, queue table, worker claim query, counter cache, balance or stock update, reservation flow, idempotency record, ledger projection, status transition, batch update, delete job, online DDL path, migration plan, or lock-sensitive read path.
|
|
40
|
+
- The risk is hot-row contention, parent-row counters, shared aggregate rows, `SELECT ... FOR UPDATE`, `FOR NO KEY UPDATE`, `FOR SHARE`, `FOR KEY SHARE`, `NOWAIT`, `SKIP LOCKED`, optimistic version checks, conditional updates, advisory locks, distributed locks backed by database state, MySQL gap or next-key locks, SQL Server lock escalation, PostgreSQL DDL lock levels, MySQL metadata locks, deadlocks, lock waits, pool waits, or idle transactions.
|
|
41
|
+
- Code or docs claim a path is safe under high write concurrency, deadlock-safe, lock-efficient, no-downtime, queue-consumer safe, stock-safe, balance-safe, order-preserving, or low-lock.
|
|
42
|
+
- A database review needs a contention pass separate from query latency, migration compatibility, transaction correctness, generic race conditions, or backend observability.
|
|
43
|
+
|
|
44
|
+
<!-- mustflow-section: do-not-use-when -->
|
|
45
|
+
## Do Not Use When
|
|
46
|
+
|
|
47
|
+
- The task is only query latency, cardinality, projection width, pagination, N+1 access, or plan shape without blocking or lock contention risk; use `database-query-bottleneck-review`.
|
|
48
|
+
- The task is primarily old-code/new-schema compatibility, DDL rollout, backfill, generated clients, or destructive migration safety; use `database-migration-change` first and this skill only for lock-contention adjunct review.
|
|
49
|
+
- The task is primarily read -> decision -> write correctness, durable constraints, rollback behavior, transaction propagation, or after-commit side effects; use `transaction-boundary-integrity-review` first and this skill only for blocking, deadlock, or hot-resource pressure.
|
|
50
|
+
- The task is generic in-memory, filesystem, queue, socket, timer, or distributed shared-state interleaving with no database lock surface; use `race-condition-review` or `concurrency-invariant-review`.
|
|
51
|
+
- The database work is a one-off, manually bounded maintenance action on tiny data with no concurrent application traffic and no production-safety claim.
|
|
52
|
+
|
|
53
|
+
<!-- mustflow-section: required-inputs -->
|
|
54
|
+
## Required Inputs
|
|
55
|
+
|
|
56
|
+
- Contended resource: row, parent row, counter row, index prefix, range predicate, gap, queue head, table, partition, metadata lock, migration lock, advisory lock key, or connection pool that concurrent work can wait on.
|
|
57
|
+
- Workload shape: write rate, same-tenant or same-resource concentration, queue consumer count, batch size, worker parallelism, retry behavior, traffic spikes, table size, and whether old transactions or long reports can overlap.
|
|
58
|
+
- Database engine and version when known: PostgreSQL, MySQL/InnoDB, SQL Server, SQLite, managed database, ORM behavior, isolation level, lock wait timeout, statement timeout, transaction timeout, and pool limit.
|
|
59
|
+
- Locking path: exact SQL or ORM calls, selected indexes, predicates, `FOR UPDATE` variant, isolation level, update order, lock order, transaction start and end, and external calls or calculations inside the transaction.
|
|
60
|
+
- Data-shape alternatives: sharded counters, append-only ledgers, reservation tables, materialized summaries, per-tenant or per-shard queue lanes, partitioning, CQRS/read models, stage-specific tables, and conditional updates.
|
|
61
|
+
- Failure and retry evidence: deadlock classification, serialization failures, lock timeout handling, optimistic-lock row count checks, full-command retry budget, idempotency keys, poison or starvation handling, and manual recovery.
|
|
62
|
+
- Observability evidence: lock-wait logs, blocked-by and blocking query context, transaction age, pool wait metrics, deadlock logs, queue lag by shard, batch progress, migration lock waits, and configured command intents.
|
|
63
|
+
|
|
64
|
+
<!-- mustflow-section: preconditions -->
|
|
65
|
+
## Preconditions
|
|
66
|
+
|
|
67
|
+
- The task matches the Use When conditions and does not match the Do Not Use When exclusions.
|
|
68
|
+
- Higher-priority instructions and `.mustflow/config/commands.toml` have been checked for the current scope.
|
|
69
|
+
- Required inputs are available, or missing engine, isolation, index, workload, lock-order, timeout, or observability evidence can be reported without guessing.
|
|
70
|
+
- Existing local patterns for ledgers, reservations, counters, queue claiming, conditional updates, optimistic locks, outbox, retry classification, lock timeouts, and lock diagnostics have been searched before adding new shapes.
|
|
71
|
+
- If the contention path affects money, credits, inventory, permissions, tenant data, or external side effects, also apply the relevant payment, credit-ledger, business-rule, security, transaction, idempotency, queue, or observability skill.
|
|
72
|
+
|
|
73
|
+
<!-- mustflow-section: allowed-edits -->
|
|
74
|
+
## Allowed Edits
|
|
75
|
+
|
|
76
|
+
- Replace shared hot-row updates with append-only events, sharded counters, reservations, snapshots, materialized summaries, or stage-specific rows when local ownership and correctness allow it.
|
|
77
|
+
- Replace select-then-update with conditional updates, atomic upserts, optimistic version checks, affected-row checks, or database constraints when they preserve the invariant and reduce waiting.
|
|
78
|
+
- Narrow transaction scope by moving calculations, external API calls, object storage, email, webhooks, sleeps, slow serialization, and user-controlled work outside the lock-holding window.
|
|
79
|
+
- Choose weaker database locks, stable lock order, `NOWAIT`, `SKIP LOCKED`, chunked batch writes, partitioned work, queue shard keys, and lock timeout policy only when the semantic tradeoff is explicit.
|
|
80
|
+
- Add focused tests, fixtures, docs, or telemetry assertions for lock-timeout handling, deadlock retry, queue claiming, conditional-update failure, optimistic-lock conflicts, and synchronized template surfaces when local patterns support them.
|
|
81
|
+
- Do not add speculative indexes, global serializable isolation, process-local mutexes, distributed locks, lock hints, or retries as magic fixes without naming the contended resource, correctness invariant, lock order, timeout behavior, and evidence gap.
|
|
82
|
+
|
|
83
|
+
<!-- mustflow-section: procedure -->
|
|
84
|
+
## Procedure
|
|
85
|
+
|
|
86
|
+
1. Name the contended database resource.
|
|
87
|
+
- Identify the row, range, index prefix, parent row, counter, queue head, table, partition, metadata object, advisory lock key, or connection pool that concurrent executions can wait on.
|
|
88
|
+
- Treat `users.balance`, `products.stock`, `counters.value`, `posts.like_count`, queue `status = 'PENDING'`, and migration metadata as contention candidates even when each single statement looks cheap.
|
|
89
|
+
2. Map the write concentration.
|
|
90
|
+
- Separate evenly distributed writes from same-account, same-product, same-tenant, same-campaign, same-post, same-day, or same-queue-head writes.
|
|
91
|
+
- If many requests must update one row to preserve a visible aggregate, ask whether the aggregate can be appended, sharded, reserved, summarized, or made eventually consistent.
|
|
92
|
+
3. Prefer append or reservation models for durable histories.
|
|
93
|
+
- Money, credits, stock, coupons, usage, entitlement, and audit-sensitive paths usually need a ledger, event, reservation, capture, or release record before a mutable current-value row.
|
|
94
|
+
- Keep snapshot or cache updates separate from the durable fact when exact current display is less valuable than write throughput and auditability.
|
|
95
|
+
4. Shorten the lock window.
|
|
96
|
+
- Finish price calculation, discount evaluation, permission checks, payload validation, and derived data construction before acquiring the lock when the decision can be revalidated cheaply.
|
|
97
|
+
- Keep only the final conditional write, version check, claim, or state transition inside the shortest transaction that preserves the invariant.
|
|
98
|
+
- Move HTTP calls, payment provider calls, email, webhooks, S3/object storage, search indexing, and queue publishing to after-commit or outbox paths.
|
|
99
|
+
5. Challenge `SELECT ... FOR UPDATE`.
|
|
100
|
+
- Do not treat `FOR UPDATE` as a general safety blanket. Check whether the selected row is the real invariant owner and whether a weaker lock, conditional update, unique constraint, optimistic version, or parent guard is sufficient.
|
|
101
|
+
- In PostgreSQL, distinguish `FOR UPDATE`, `FOR NO KEY UPDATE`, `FOR SHARE`, and `FOR KEY SHARE` when key changes and foreign-key protection matter.
|
|
102
|
+
- Remember that row locks block competing writes and locks, not ordinary MVCC reads.
|
|
103
|
+
6. Review MySQL/InnoDB index and range locking.
|
|
104
|
+
- Treat row locks as index-record locks. If the predicate lacks the right index, the engine may scan and lock more records than the business object implies.
|
|
105
|
+
- Check gap and next-key locks for range predicates under InnoDB defaults. A range can block inserts into values that do not yet exist.
|
|
106
|
+
- Consider `READ COMMITTED` only after deciding whether phantom rows are acceptable for the business rule.
|
|
107
|
+
7. Match indexes to lock footprint, not only speed.
|
|
108
|
+
- For updates and deletes, ask how many index records the engine must inspect before finding the target set.
|
|
109
|
+
- Add or reshape indexes only when the predicate, write cost, uniqueness, migration lock behavior, and workload justify reducing the lock footprint.
|
|
110
|
+
8. Make uniqueness and conditional writes do the guarding.
|
|
111
|
+
- Replace `SELECT missing -> INSERT` with unique constraints and insert-or-conflict handling.
|
|
112
|
+
- Replace stock, capacity, status, lease, and version updates with single conditional updates whose affected-row count is checked.
|
|
113
|
+
- For long user think-time, use optimistic version checks instead of holding database locks across the think time.
|
|
114
|
+
9. Design queue tables around claiming, not polling.
|
|
115
|
+
- Use `SKIP LOCKED` or equivalent only for queue claiming where incomplete views are expected.
|
|
116
|
+
- Avoid one global `PENDING` lane that all workers scrape from the same index head. Add shard keys, `available_at`, priority, attempt count, `locked_at`, and deterministic ordering when the queue table is the contention point.
|
|
117
|
+
- Check starvation and fairness when high-priority or old locked rows can hide lower-priority work.
|
|
118
|
+
10. Fix deadlock shape before blaming the engine.
|
|
119
|
+
- Establish a global order for touching accounts, products, rows, tables, partitions, or advisory lock keys.
|
|
120
|
+
- Do not trust `WHERE id IN (...)` or unordered ORM collections to acquire locks in a stable order when many rows are updated.
|
|
121
|
+
- Treat deadlock and serialization failures as normal retry branches only when the whole command is idempotent and retryable.
|
|
122
|
+
11. Chunk large writes and deletes.
|
|
123
|
+
- Large `UPDATE` and `DELETE` operations can hold many locks, inflate undo or WAL, lag replicas, block vacuum or purge, and escalate locks on engines that support escalation.
|
|
124
|
+
- Prefer bounded key-range batches, checkpoints, pause or resume controls, and validation counts instead of one heroic statement on production-sized data.
|
|
125
|
+
12. Use partitioning and table splits as contention boundaries.
|
|
126
|
+
- Partition by date, tenant, region, shard, or lifecycle stage only when it separates write conflicts and still fits the query model.
|
|
127
|
+
- Split state-machine rows into payments, fulfillments, shipments, settlements, or similar stage tables when independent workflows should not rewrite the same row.
|
|
128
|
+
13. Review foreign-key and parent-row side effects.
|
|
129
|
+
- Parent deletes, key updates, child inserts, and child updates can create hidden locks around referential integrity.
|
|
130
|
+
- High-traffic child event tables that all reference a hot parent row may need a different ownership model, deferred aggregate, or explicit parent-row contention budget.
|
|
131
|
+
14. Treat DDL and metadata locks as production traffic.
|
|
132
|
+
- Online index creation, concurrent index creation, constraint validation, metadata commits, and table rewrites can still wait on old transactions or briefly block application queries.
|
|
133
|
+
- Kill or drain `idle in transaction` and long-running transactions before migration windows when the repository owns that operational procedure; treat idle-in-transaction blockers as lock-contention inputs, not post-incident trivia.
|
|
134
|
+
- Prefer short lock timeouts for online DDL attempts that should back off rather than queue behind production traffic.
|
|
135
|
+
15. Set lock timeout policy by operation.
|
|
136
|
+
- Interactive requests, checkout, admin jobs, backfills, migrations, and reconciliation should not share one infinite wait policy.
|
|
137
|
+
- Distinguish lock timeout, statement timeout, transaction timeout, pool wait timeout, and provider timeout in logs and retry handling.
|
|
138
|
+
16. Separate lock waits from connection-pool waits.
|
|
139
|
+
- A request can look like a database lock incident while it is actually stuck waiting for a connection held by wide transactions, `REQUIRES_NEW`, per-item transactions, or slow external calls inside transactions.
|
|
140
|
+
- Review pool size, transaction width, nested transaction behavior, and per-request database checkout count before changing SQL locks.
|
|
141
|
+
17. Add observability that names both waiter and blocker.
|
|
142
|
+
- Logs should identify operation, resource key, transaction age, lock wait duration, timeout class, retry attempt, idempotency key, queue shard, batch cursor, and blocking query or session when available.
|
|
143
|
+
- Metrics should avoid unbounded labels but preserve table or operation class, lock-wait bucket, pool-wait bucket, deadlock count, timeout count, and queue lag by bounded shard.
|
|
144
|
+
- For PostgreSQL, MySQL, SQL Server, or managed database diagnostics, use repository-approved observability paths and report manual-only diagnostics when no configured command exists.
|
|
145
|
+
18. Label evidence honestly.
|
|
146
|
+
- Static review can identify likely lock contention but cannot prove p95 lock wait, deadlock rate, gap-lock behavior, or migration lock safety under production data.
|
|
147
|
+
- Treat engine docs, plan output, deadlock logs, `pg_locks`, InnoDB status, SQL Server DMVs, Query Store, APM traces, and production telemetry as stronger evidence only when they match the repository engine, version, schema, and workload.
|
|
148
|
+
|
|
149
|
+
<!-- mustflow-section: postconditions -->
|
|
150
|
+
## Postconditions
|
|
151
|
+
|
|
152
|
+
- The contended resource, workload concentration, lock path, lock order, transaction width, timeout policy, retry behavior, queue claim model, DDL or metadata lock exposure, and observability evidence are explicit.
|
|
153
|
+
- Hot rows, mutable counter caches, select-then-update races, over-strong locks, missing lock-footprint indexes, range or gap-lock surprises, unordered multi-row updates, large unchunked writes, queue head contention, hidden FK or parent-row locks, and idle-transaction DDL blockers are fixed or reported.
|
|
154
|
+
- Correctness, auditability, idempotency, ordering, tenant isolation, and user-visible truth remain intact or are reported as tradeoffs.
|
|
155
|
+
- Lock-safety claims are backed by configured tests, engine evidence, observability evidence, or labeled as static review risk.
|
|
156
|
+
|
|
157
|
+
<!-- mustflow-section: verification -->
|
|
158
|
+
## Verification
|
|
159
|
+
|
|
160
|
+
Use configured oneshot command intents when available:
|
|
161
|
+
|
|
162
|
+
- `changes_status`
|
|
163
|
+
- `changes_diff_summary`
|
|
164
|
+
- `lint`
|
|
165
|
+
- `build`
|
|
166
|
+
- `test_related`
|
|
167
|
+
- `test`
|
|
168
|
+
- `docs_validate_fast`
|
|
169
|
+
- `test_release`
|
|
170
|
+
- `mustflow_check`
|
|
171
|
+
|
|
172
|
+
Use the narrowest configured test, build, docs, release, or mustflow intent that covers the changed lock-sensitive path and synchronized template surfaces. Do not infer raw database shells, live lock dashboards, production lock queries, migration execution, load tests, stress tests, server processes, watcher processes, or package-manager commands outside the command contract.
|
|
173
|
+
|
|
174
|
+
<!-- mustflow-section: failure-handling -->
|
|
175
|
+
## Failure Handling
|
|
176
|
+
|
|
177
|
+
- If a configured command fails, preserve the failing intent, failing assertion or output tail, and the lock-sensitive invariant it exercised before editing again.
|
|
178
|
+
- If the engine, isolation level, index shape, workload, table size, lock timeout, or observability surface is unknown, report static lock-contention risk instead of claiming the path is safe.
|
|
179
|
+
- If a safe fix requires schema changes, online DDL, partitioning, queue redesign, outbox workers, materialized summaries, load tests, production diagnostics, or provider-console changes outside the current scope, report the missing boundary.
|
|
180
|
+
- If no configured command can prove concurrent lock behavior, report the missing manual evidence and complete the configured checks that are available.
|
|
181
|
+
|
|
182
|
+
<!-- mustflow-section: output-format -->
|
|
183
|
+
## Output Format
|
|
184
|
+
|
|
185
|
+
- Database lock-contention surface reviewed
|
|
186
|
+
- Contended resource, workload concentration, lock path, engine and isolation evidence
|
|
187
|
+
- Hot-row, event or reservation model, conditional write, lock strength, index lock footprint, gap or next-key lock, queue claim, lock order, batch chunking, partition, FK or parent-row, DDL or metadata lock, timeout, pool wait, retry, and observability findings
|
|
188
|
+
- Lock-contention fix made or recommended
|
|
189
|
+
- Evidence level: configured-test evidence, engine evidence, production telemetry, static review risk, manual-only, missing, or not applicable
|
|
190
|
+
- Command intents run
|
|
191
|
+
- Skipped lock diagnostics and reasons
|
|
192
|
+
- Remaining database lock-contention risk
|
|
@@ -2,11 +2,11 @@
|
|
|
2
2
|
mustflow_doc: skill.database-migration-change
|
|
3
3
|
locale: en
|
|
4
4
|
canonical: true
|
|
5
|
-
revision:
|
|
5
|
+
revision: 2
|
|
6
6
|
lifecycle: mustflow-owned
|
|
7
7
|
authority: procedure
|
|
8
8
|
name: database-migration-change
|
|
9
|
-
description: Apply this skill when database migration files, schema migration history, ORM schema migrations, generated clients, schema dumps, SQL snapshots, backfills, rolling deploy compatibility, expand-and-contract changes, destructive database changes, migration rollback claims, or production database migration procedures are created, changed, reviewed, or reported.
|
|
9
|
+
description: Apply this skill when database migration files, schema migration history, ORM schema migrations, generated clients, schema dumps, SQL snapshots, online DDL, large indexes, constraints, backfills, rolling deploy compatibility, expand-and-contract changes, destructive database changes, migration rollback or roll-forward claims, cut-over plans, lock or timeout policy, replication lag risk, migration observability, or production database migration procedures are created, changed, reviewed, or reported.
|
|
10
10
|
metadata:
|
|
11
11
|
mustflow_schema: "1"
|
|
12
12
|
mustflow_kind: procedure
|
|
@@ -29,16 +29,17 @@ metadata:
|
|
|
29
29
|
<!-- mustflow-section: purpose -->
|
|
30
30
|
## Purpose
|
|
31
31
|
|
|
32
|
-
Keep database migrations safe for running systems by checking deploy compatibility, data preservation, backfill behavior, generated artifacts, ORM contracts, and
|
|
32
|
+
Keep database migrations safe for running systems by checking deploy compatibility, data preservation, lock behavior, online DDL limits, backfill behavior, generated artifacts, ORM contracts, observability, and recovery reality.
|
|
33
33
|
|
|
34
34
|
Do not treat migration authoring as "make a file that applies locally." Treat it as "old code and new code must survive the same database during rollout."
|
|
35
|
+
Migration incidents usually happen in the interval where old code, new code, old data, and new data are all alive at once. Design that interval first.
|
|
35
36
|
|
|
36
37
|
<!-- mustflow-section: use-when -->
|
|
37
38
|
## Use When
|
|
38
39
|
|
|
39
40
|
- A database migration file, migration history entry, schema dump, ORM schema, SQL snapshot, generated client, seed, fixture, schema validator, or migration documentation is created or changed.
|
|
40
41
|
- A change adds, removes, renames, splits, merges, backfills, rewrites, validates, constrains, indexes, foreign-keys, type-changes, defaults, nullable rules, enum values, tables, columns, generated columns, triggers, views, functions, row-level policies, or data migrations.
|
|
41
|
-
- A task mentions rolling deploy, expand-and-contract, online migration, backfill, production schema change, rollback, down migration, migration lock, DDL transaction, generated ORM client, migration drift, schema drift, or database migration safety.
|
|
42
|
+
- A task mentions rolling deploy, expand-and-contract, online migration, backfill, production schema change, rollback, roll-forward, down migration, migration lock, lock timeout, statement timeout, DDL transaction, `CREATE INDEX CONCURRENTLY`, MySQL `ALGORITHM=INSTANT`, MySQL `LOCK=NONE`, generated ORM client, migration drift, schema drift, or database migration safety.
|
|
42
43
|
- Prisma, Drizzle, TypeORM, Rails Active Record, Django migrations, Alembic, Diesel, Ecto, Flyway, Liquibase, Knex, Sequelize, SQLx, or another migration tool changes schema, generated output, migration metadata, or deployment behavior.
|
|
43
44
|
- A final report claims a database migration is safe, reversible, applied, validated, production-ready, no-downtime, rollback-safe, or tested from an old schema.
|
|
44
45
|
|
|
@@ -55,8 +56,8 @@ Do not treat migration authoring as "make a file that applies locally." Treat it
|
|
|
55
56
|
- Source schema, target schema, migration files, migration history table or metadata, generated clients, schema dumps, SQL snapshots, seeds, fixtures, and affected queries.
|
|
56
57
|
- Migration tool and ecosystem: Prisma, Drizzle, TypeORM, Rails, Django, Alembic, Diesel, Ecto, Flyway, Liquibase, Knex, Sequelize, SQLx, raw SQL, or another declared tool.
|
|
57
58
|
- Deployment shape: single-step deploy, rolling deploy, blue-green, multiple app versions, background workers, read replicas, multiple services, serverless functions, mobile clients, or external integrations.
|
|
58
|
-
- Database engine and operational surface: PostgreSQL, MySQL, SQLite, SQL Server, managed database, migration lock behavior, DDL transaction behavior, online DDL options, table size, expected lock time, statement timeout, lock timeout, and restore capability when known.
|
|
59
|
-
- Data preservation needs, compatibility window, backfill size, batch strategy,
|
|
59
|
+
- Database engine and operational surface: PostgreSQL, MySQL, SQLite, SQL Server, managed database, migration lock behavior, DDL transaction behavior, online DDL options, table size, write load, long-running transactions, replication or CDC topology, expected lock time, statement timeout, lock timeout, and restore capability when known.
|
|
60
|
+
- Data preservation needs, compatibility window, backfill size, batch strategy, cursor or checkpoint marker, validation query, observability query, rollback or roll-forward type, cut-over control, and whether old code can run after the new schema lands.
|
|
60
61
|
- Relevant command-intent entries for build, generated-output checks, tests, docs, release, and mustflow validation.
|
|
61
62
|
|
|
62
63
|
<!-- mustflow-section: preconditions -->
|
|
@@ -64,7 +65,7 @@ Do not treat migration authoring as "make a file that applies locally." Treat it
|
|
|
64
65
|
|
|
65
66
|
- The task matches the Use When conditions and does not match the Do Not Use When exclusions.
|
|
66
67
|
- Higher-priority instructions and `.mustflow/config/commands.toml` have been checked for the current scope.
|
|
67
|
-
- The migration is classified before editing as expand, backfill, switch, contract, destructive, data-only, schema-only, generated-output-only, ORM metadata-only, or
|
|
68
|
+
- The migration is classified before editing as expand, backfill, switch, contract, destructive, data-only, schema-only, generated-output-only, ORM metadata-only, cut-over, or recovery documentation.
|
|
68
69
|
- If personal data, tenant isolation, authorization, audit, retention, or secrets are involved, also use `security-privacy-review`.
|
|
69
70
|
- If public API response shape changes because of the migration, also use `api-contract-change`.
|
|
70
71
|
- If file paths or storage keys change with the database migration, also use `file-path-cross-platform-change`.
|
|
@@ -73,7 +74,7 @@ Do not treat migration authoring as "make a file that applies locally." Treat it
|
|
|
73
74
|
## Allowed Edits
|
|
74
75
|
|
|
75
76
|
- Update migration files, ORM schema files, generated client expectations, schema dumps, SQL snapshots, seeds, fixtures, compatibility code, backfill code, validation checks, docs, and tests directly required by the migration.
|
|
76
|
-
- Prefer expand-and-contract for live systems: add compatible shape, backfill safely, switch reads and writes, then contract only after compatibility is proven.
|
|
77
|
+
- Prefer expand-and-contract for live systems: add compatible shape, dual-write or compatibility-read where needed, backfill safely, switch reads and writes, then contract only after compatibility is proven.
|
|
77
78
|
- Keep destructive cleanup separate from expansion unless the repository explicitly proves a single-step deployment is safe.
|
|
78
79
|
- Do not weaken tests, delete migration history, hand-edit generated client output, suppress migration drift, or claim rollback safety for lossy changes.
|
|
79
80
|
|
|
@@ -97,34 +98,70 @@ Do not treat migration authoring as "make a file that applies locally." Treat it
|
|
|
97
98
|
- New code after backfill.
|
|
98
99
|
- New code after contract.
|
|
99
100
|
If any required state fails, the migration is not rolling-deploy safe.
|
|
100
|
-
5.
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
101
|
+
5. Split the deployment plan into expand, backfill, switch, and contract phases.
|
|
102
|
+
- Expansion adds shapes old code can ignore and new code can start writing.
|
|
103
|
+
- Backfill is bounded, restartable, idempotent, observable, and separately validated.
|
|
104
|
+
- Switch changes read paths through a feature flag, rollout gate, tenant gate, or compatible deploy step where possible.
|
|
105
|
+
- Contract removes old shapes only after at least one compatibility window proves no code, job, report, or manual SQL still depends on them.
|
|
106
|
+
6. For column add, decide nullability, default behavior, backfill strategy, write path, read fallback, index need, and when a future `NOT NULL` or constraint can be enforced.
|
|
107
|
+
- Add nullable first unless a proven engine/version/table-size path makes the non-null default safe.
|
|
108
|
+
- Do not assume a database default backfills existing rows or matches ORM, API, batch, or application defaults.
|
|
109
|
+
- Enforce `NOT NULL` only after new writes populate the column, old rows are backfilled, and missing-value validation has passed.
|
|
110
|
+
7. For column drop, first prove all reads, writes, generated clients, old app versions, jobs, analytics, exports, seeds, fixtures, docs, BI queries, support SQL, and external consumers stopped using the column. Treat `DROP COLUMN` as a contract phase, not as the first migration.
|
|
111
|
+
8. For rename, do not implement rename as drop plus add unless data loss is explicitly intended and approved. Prefer add new column, dual-write or copy, backfill, switch reads, validate, then drop old column later.
|
|
112
|
+
9. For type changes, check whether the database rewrites the table, whether old values can fail conversion, whether indexes or constraints rebuild, whether application serializers change, and whether API or generated client types change.
|
|
113
|
+
10. For nullable and default changes, distinguish schema default from application default. Change application writes first when defaults must stay compatible across old and new versions.
|
|
114
|
+
11. For constraints and foreign keys, use staged validation when the database supports it.
|
|
115
|
+
- PostgreSQL `NOT VALID` constraints and later `VALIDATE CONSTRAINT` can avoid validating old rows during the first lock-sensitive change while still protecting new writes.
|
|
116
|
+
- Foreign keys on large or hot tables need separate add, repair/backfill, validate, and fallback planning rather than one heroic migration.
|
|
117
|
+
12. For indexes, check table size, write load, lock behavior, concurrent or online index support, uniqueness validation, existing duplicates, and whether generated ORM queries will use the index.
|
|
118
|
+
- PostgreSQL `CREATE INDEX CONCURRENTLY` avoids blocking ordinary writes but still scans more than once, waits for old transactions, consumes I/O, and cannot run inside a transaction block.
|
|
119
|
+
- MySQL online DDL and `ALGORITHM=INSTANT` have version, row-format, index, row-size, and operation limits; specify `ALGORITHM=INSTANT` or `LOCK=NONE` only when unsupported fallback should fail instead of silently rebuilding a table.
|
|
120
|
+
- Treat index deletion as a separate risk: usage counters can lie after restarts, stats resets, monthly jobs, or emergency queries.
|
|
121
|
+
13. Review lock and timeout policy.
|
|
122
|
+
- PostgreSQL `ALTER TABLE` often takes strong locks unless a subcommand documents a lower level.
|
|
123
|
+
- Use short `lock_timeout` and an appropriate `statement_timeout` policy when the repository owns that migration surface.
|
|
124
|
+
- Do not wrap several DDL statements in one transaction just because the file looks cleaner; locks held until commit can block unrelated traffic.
|
|
125
|
+
- Very short metadata-only changes on the same table may be bundled only after engine/version/table-state evidence shows each subcommand stays metadata-only.
|
|
126
|
+
14. For enum, partition, and table-ownership changes, check engine-specific limits.
|
|
127
|
+
- Enum value additions, removals, or renames can break old code, generated unions, rollback, defaults, and storage layout.
|
|
128
|
+
- Partition attach can scan existing rows unless a suitable `CHECK` constraint proves the range first.
|
|
129
|
+
- Table split, table merge, or relationship rewrite must preserve stable identifiers, foreign keys, audit references, external IDs, permissions, search documents, exports, and old-to-new mapping until all callers switch.
|
|
130
|
+
15. For backfills, make them bounded, restartable, observable, and validated. Define batch size, cursor-based ordering key such as `id > last_id`, checkpoint, retry behavior, idempotency, timeout, lock expectation, throttle or pause/resume control, dead-letter or manual review behavior, and validation queries.
|
|
131
|
+
16. Do not run or recommend full-table updates on production-sized data without measured volume, lock expectation, WAL or undo impact, replication lag risk, batch plan, timeout policy, and recovery plan.
|
|
132
|
+
17. Review replication, CDC, and long-running transaction interactions.
|
|
133
|
+
- Online DDL can leave replicas, read traffic, backups, CDC connectors, or failover readiness behind even when the primary looks healthy.
|
|
134
|
+
- PostgreSQL concurrent index builds can wait on old transactions, idle-in-transaction sessions, backups, or long reports.
|
|
135
|
+
- MySQL online DDL can still need short exclusive locks at the beginning or final phase; plan cut-over timing rather than trusting ETA.
|
|
136
|
+
18. Review cut-over control for ghost-table, copy-and-swap, or dual-write migrations.
|
|
137
|
+
- The dangerous moment is usually the final swap, name change, or read-path flip, not the long copy.
|
|
138
|
+
- Preserve a postpone, pause, resume, throttle, or manual approval point when the repository's migration tool supports it.
|
|
139
|
+
- Monitor dual-write mismatch and sample old/new values during the compatibility window; code intent is not proof that every path writes both sides.
|
|
140
|
+
19. Prepare observability before apply.
|
|
141
|
+
- Pair the migration with read-only progress and safety queries for lock waits, index build progress, replication lag, backfill cursor, skipped rows, failed rows, duplicate rows, missing rows, dead tuples, or estimated remaining range when the engine supports them.
|
|
142
|
+
- Log or report dry-run selection counts, apply counts, skip reasons, batch durations, and recovery handles.
|
|
143
|
+
- A final `done` line is not enough evidence for a live migration.
|
|
144
|
+
20. Decide rollback honestly and prefer roll-forward for partial live changes.
|
|
145
|
+
- Reversible: schema-only and data-preserving.
|
|
146
|
+
- App rollback: old and new code both tolerate the expanded shape, so the read path can move back without losing new writes.
|
|
147
|
+
- Forward-fix preferred: partial live migration can be corrected without restoring.
|
|
148
|
+
- Restore required: deletes, table merges, generated IDs, hashing, encryption, irreversible type conversions, external side effects, or lossy transforms.
|
|
149
|
+
Do not promise rollback for changes that cannot reconstruct old values.
|
|
150
|
+
21. Keep external side effects out of database migrations unless the repository has an explicit recovery model. Sending emails, calling payment APIs, deleting files, or mutating external providers from a migration usually breaks rollback.
|
|
151
|
+
22. Check generated surfaces after schema changes: ORM clients, types, SQL snapshots, schema dumps, OpenAPI or GraphQL projections, API mocks, fixtures, seeds, admin screens, analytics, ETL, BI queries, and docs examples.
|
|
152
|
+
23. Review ORM-specific traps.
|
|
114
153
|
- Prisma generated client and migration history must match the migration files that production applies.
|
|
115
154
|
- Drizzle schema exports and generated SQL or snapshots must not drift.
|
|
116
155
|
- TypeORM production `synchronize` must not be used as a migration strategy.
|
|
117
156
|
- Django rename detection and autogeneration must be reviewed so rename does not become delete and create.
|
|
118
157
|
- Alembic autogenerate output is a candidate, not a reviewed migration.
|
|
119
158
|
- Rails migrations should not depend on current model callbacks or validations when historical data can outlive current model code.
|
|
120
|
-
|
|
121
|
-
-
|
|
122
|
-
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
21. Check dependent surfaces: application code, background jobs, cron tasks, workers, ETL, reports, admin tools, data exports, imports, mobile or older clients, webhooks, API clients, generated SDKs, test fixtures, seeds, docs, and monitoring.
|
|
127
|
-
22. Select verification from the command contract. Major schema changes, generated client changes, rollback-sensitive changes, security-sensitive migrations, and production deployment changes need broader verification than local schema-only edits.
|
|
159
|
+
24. Add or check automated guardrails when the repository owns migration linting.
|
|
160
|
+
- Flag raw `CREATE INDEX` on large PostgreSQL tables when `CONCURRENTLY` is expected.
|
|
161
|
+
- Flag first-phase `DROP COLUMN`, large-table `SET NOT NULL`, unvalidated foreign keys, transaction-wrapped concurrent index creation, unbounded `UPDATE`, offset-based backfills, and unchecked destructive operations.
|
|
162
|
+
25. Rehearse from the previous production-like schema when possible. A migration that only applies to a freshly generated schema is not enough.
|
|
163
|
+
26. Check dependent surfaces: application code, background jobs, cron tasks, workers, ETL, reports, admin tools, data exports, imports, mobile or older clients, webhooks, API clients, generated SDKs, test fixtures, seeds, docs, and monitoring.
|
|
164
|
+
27. Select verification from the command contract. Major schema changes, generated client changes, rollback-sensitive changes, security-sensitive migrations, and production deployment changes need broader verification than local schema-only edits.
|
|
128
165
|
|
|
129
166
|
<!-- mustflow-section: postconditions -->
|
|
130
167
|
## Postconditions
|
|
@@ -132,9 +169,10 @@ Do not treat migration authoring as "make a file that applies locally." Treat it
|
|
|
132
169
|
- Source schema, target schema, migration files, generated artifacts, schema dumps, seeds, fixtures, and dependent code agree.
|
|
133
170
|
- Expand, backfill, switch, and contract phases are separated or explicitly proven unnecessary.
|
|
134
171
|
- Old-code/new-schema and new-code/expanded-schema compatibility is classified.
|
|
135
|
-
- Backfill and validation behavior is bounded, restartable, and checkable where relevant.
|
|
136
|
-
-
|
|
137
|
-
-
|
|
172
|
+
- Backfill and validation behavior is cursor-based or otherwise bounded, restartable, idempotent, observable, and checkable where relevant.
|
|
173
|
+
- Lock levels, online DDL support, long-running transaction waits, replication lag, cut-over control, timeout policy, and observability queries are explicit where production data may be affected.
|
|
174
|
+
- Rollback claims distinguish schema rollback, data rollback, app rollback, roll-forward, forward-fix, and restore-required cases.
|
|
175
|
+
- Destructive changes and production lock risks are either deferred, measured, guarded, or reported as remaining risk.
|
|
138
176
|
|
|
139
177
|
<!-- mustflow-section: verification -->
|
|
140
178
|
## Verification
|
|
@@ -158,8 +196,10 @@ Prefer configured migration dry-run, generated-output, schema-diff, or database
|
|
|
158
196
|
|
|
159
197
|
- If old/new application compatibility is unknown, do not call the migration rolling-deploy safe.
|
|
160
198
|
- If production table size, lock behavior, or validation cost is unknown, report the operation as production-risky.
|
|
199
|
+
- If online DDL support, long-running transaction behavior, replication lag, or cut-over control is unknown, report the migration as operationally unproven.
|
|
161
200
|
- If an autogenerator proposes drop/create for a rename, stop and rewrite the migration plan.
|
|
162
201
|
- If a migration is lossy, do not claim rollback beyond restore or forward corrective migration.
|
|
202
|
+
- If a backfill is not idempotent, restartable, observable, and throttled or bounded, keep it out of a production migration claim.
|
|
163
203
|
- If generated clients or schema dumps drift, fix the source of truth and regenerated surfaces together.
|
|
164
204
|
- If configured verification is missing, report the missing command intent instead of inferring package-manager, ORM, or migration-tool commands.
|
|
165
205
|
|
|
@@ -170,7 +210,9 @@ Prefer configured migration dry-run, generated-output, schema-diff, or database
|
|
|
170
210
|
- Tool and database engine surface inspected
|
|
171
211
|
- Source schema, target schema, and migration phase
|
|
172
212
|
- Old-code/new-schema and new-code/expanded-schema compatibility
|
|
173
|
-
-
|
|
213
|
+
- Expand/backfill/switch/contract plan and destructive cleanup timing
|
|
214
|
+
- Backfill cursor, idempotency, throttle, pause/resume, validation, lock, timeout, replication, cut-over, and observability classification
|
|
215
|
+
- Rollback, app rollback, roll-forward, forward-fix, and restore-required classification
|
|
174
216
|
- ORM/generated client/schema dump/snapshot surfaces synchronized
|
|
175
217
|
- Dependent surfaces checked
|
|
176
218
|
- Command intents run
|