@atlashub/smartstack-cli 2.9.0 → 3.0.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/.documentation/business-analyse.html +81 -17
- package/dist/mcp-entry.mjs +1302 -223
- package/dist/mcp-entry.mjs.map +1 -1
- package/package.json +1 -1
- package/templates/agents/efcore/db-deploy.md +1 -1
- package/templates/agents/efcore/migration.md +26 -10
- package/templates/agents/efcore/rebase-snapshot.md +24 -7
- package/templates/agents/efcore/squash.md +73 -57
- package/templates/agents/gitflow/commit.md +138 -18
- package/templates/agents/gitflow/exec.md +1 -1
- package/templates/agents/gitflow/finish.md +79 -62
- package/templates/agents/gitflow/init-clone.md +186 -0
- package/templates/agents/gitflow/init-detect.md +137 -0
- package/templates/agents/gitflow/init-validate.md +210 -0
- package/templates/agents/gitflow/init.md +231 -74
- package/templates/agents/gitflow/merge.md +65 -33
- package/templates/agents/gitflow/pr.md +93 -49
- package/templates/agents/gitflow/start.md +76 -33
- package/templates/agents/gitflow/status.md +41 -71
- package/templates/hooks/appsettings-guard.sh +76 -0
- package/templates/hooks/ef-migration-check.md +1 -1
- package/templates/hooks/hooks.json +9 -0
- package/templates/project/test-frontend/msw/handlers.ts +58 -0
- package/templates/project/test-frontend/msw/server.ts +25 -0
- package/templates/project/test-frontend/setup.ts +16 -0
- package/templates/project/test-frontend/test-utils.tsx +59 -0
- package/templates/project/test-frontend/vitest.config.ts +31 -0
- package/templates/skills/_resources/config-safety.md +61 -0
- package/templates/skills/_resources/formatting-guide.md +2 -2
- package/templates/skills/application/SKILL.md +12 -3
- package/templates/skills/application/steps/step-04-backend.md +21 -0
- package/templates/skills/application/steps/step-07-tests.md +259 -120
- package/templates/skills/business-analyse/SKILL.md +57 -28
- package/templates/skills/business-analyse/_shared.md +70 -39
- package/templates/skills/business-analyse/html/ba-interactive.html +2622 -0
- package/templates/skills/business-analyse/questionnaire/00-application.md +123 -131
- package/templates/skills/business-analyse/questionnaire/01-context.md +173 -24
- package/templates/skills/business-analyse/questionnaire/02-stakeholders.md +170 -50
- package/templates/skills/business-analyse/questionnaire/03-scope.md +154 -48
- package/templates/skills/business-analyse/questionnaire/10-documentation.md +1 -1
- package/templates/skills/business-analyse/questionnaire/14-risk-assumptions.md +135 -0
- package/templates/skills/business-analyse/questionnaire/15-success-metrics.md +136 -0
- package/templates/skills/business-analyse/questionnaire.md +55 -46
- package/templates/skills/business-analyse/steps/step-00-init.md +24 -2
- package/templates/skills/business-analyse/steps/step-01-cadrage.md +31 -20
- package/templates/skills/business-analyse/steps/step-03-specify.md +1 -0
- package/templates/skills/business-analyse/steps/step-05-handoff.md +103 -1
- package/templates/skills/business-analyse/steps/step-06-extract.md +518 -0
- package/templates/skills/check-version/SKILL.md +1 -1
- package/templates/skills/efcore/steps/db/step-deploy.md +22 -3
- package/templates/skills/efcore/steps/db/step-reset.md +27 -4
- package/templates/skills/efcore/steps/db/step-seed.md +46 -2
- package/templates/skills/efcore/steps/db/step-status.md +14 -0
- package/templates/skills/efcore/steps/migration/step-01-check.md +31 -5
- package/templates/skills/efcore/steps/migration/step-02-create.md +20 -4
- package/templates/skills/efcore/steps/rebase-snapshot/step-03-create.md +60 -0
- package/templates/skills/efcore/steps/shared/step-00-init.md +47 -8
- package/templates/skills/efcore/steps/squash/step-03-create.md +27 -5
- package/templates/skills/gitflow/SKILL.md +91 -29
- package/templates/skills/gitflow/_shared.md +144 -2
- package/templates/skills/gitflow/phases/status.md +11 -1
- package/templates/skills/gitflow/steps/step-commit.md +1 -1
- package/templates/skills/gitflow/steps/step-init.md +202 -39
- package/templates/skills/gitflow/templates/config.json +10 -1
- package/templates/skills/ralph-loop/steps/step-03-commit.md +2 -2
- package/templates/skills/validate-feature/SKILL.md +83 -0
- package/templates/skills/validate-feature/steps/step-01-compile.md +38 -0
- package/templates/skills/validate-feature/steps/step-02-unit-tests.md +45 -0
- package/templates/skills/validate-feature/steps/step-03-integration-tests.md +53 -0
- package/templates/skills/validate-feature/steps/step-04-api-smoke.md +157 -0
|
@@ -29,6 +29,16 @@ Populate the database with test or initial data using EF Core conventions.
|
|
|
29
29
|
### 1. Environment Check
|
|
30
30
|
|
|
31
31
|
```bash
|
|
32
|
+
# Validate required variables from step-00-init
|
|
33
|
+
for VAR_NAME in DBCONTEXT DBCONTEXT_TYPE INFRA_PROJECT STARTUP_PROJECT SELECTED_ENV; do
|
|
34
|
+
eval VAR_VALUE=\$$VAR_NAME
|
|
35
|
+
if [ -z "$VAR_VALUE" ]; then
|
|
36
|
+
echo "ERROR: Required variable $VAR_NAME is not set"
|
|
37
|
+
echo "Run step-00-init first"
|
|
38
|
+
exit 1
|
|
39
|
+
fi
|
|
40
|
+
done
|
|
41
|
+
|
|
32
42
|
echo "Seed Configuration"
|
|
33
43
|
echo "=================="
|
|
34
44
|
echo ""
|
|
@@ -118,9 +128,10 @@ echo ""
|
|
|
118
128
|
echo "Running seeder class..."
|
|
119
129
|
|
|
120
130
|
dotnet run --project "$STARTUP_PROJECT" -- --seed
|
|
131
|
+
EXIT_CODE=$?
|
|
121
132
|
|
|
122
|
-
if [
|
|
123
|
-
echo "Seed command failed or not supported
|
|
133
|
+
if [ $EXIT_CODE -ne 0 ]; then
|
|
134
|
+
echo "Seed command failed or not supported (exit code: $EXIT_CODE)"
|
|
124
135
|
echo "Check if --seed argument is implemented in Program.cs"
|
|
125
136
|
fi
|
|
126
137
|
```
|
|
@@ -239,6 +250,39 @@ builder.HasData(new User {
|
|
|
239
250
|
|
|
240
251
|
---
|
|
241
252
|
|
|
253
|
+
## BOTH CONTEXTS:
|
|
254
|
+
|
|
255
|
+
If `RUN_BOTH=true` (auto-detected for client projects with SmartStack NuGet):
|
|
256
|
+
|
|
257
|
+
Run the seed sequence for both contexts, in order:
|
|
258
|
+
|
|
259
|
+
```bash
|
|
260
|
+
# 1. Seed CoreDbContext first (system data: Users, Roles, Permissions...)
|
|
261
|
+
echo "=== Seeding CoreDbContext (core schema) ==="
|
|
262
|
+
DBCONTEXT="CoreDbContext"
|
|
263
|
+
# Run steps 2-6 with CoreDbContext...
|
|
264
|
+
|
|
265
|
+
# 2. Then ExtensionsDbContext (client data)
|
|
266
|
+
echo ""
|
|
267
|
+
echo "=== Seeding ExtensionsDbContext (extensions schema) ==="
|
|
268
|
+
DBCONTEXT="ExtensionsDbContext"
|
|
269
|
+
# Run steps 2-6 with ExtensionsDbContext...
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
**Order matters:** Core MUST be seeded first (Extensions may reference Core data via foreign keys).
|
|
273
|
+
|
|
274
|
+
---
|
|
275
|
+
|
|
276
|
+
## OPTIONS:
|
|
277
|
+
|
|
278
|
+
| Option | Description |
|
|
279
|
+
|--------|-------------|
|
|
280
|
+
| `--env {name}` | Use appsettings.{name}.json |
|
|
281
|
+
| `--context {name}` | Specify DbContext |
|
|
282
|
+
| `--method {name}` | Force seed method (hasdata, seeder-class, cli-argument) |
|
|
283
|
+
|
|
284
|
+
---
|
|
285
|
+
|
|
242
286
|
## COMPLETION:
|
|
243
287
|
|
|
244
288
|
Seed data applied. Use `/efcore db-status` to verify.
|
|
@@ -18,6 +18,20 @@ Display comprehensive status of EF Core migrations and database connection.
|
|
|
18
18
|
|
|
19
19
|
## EXECUTION SEQUENCE:
|
|
20
20
|
|
|
21
|
+
### 0. Validate Required Variables
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
# Validate required variables from step-00-init
|
|
25
|
+
for VAR_NAME in DBCONTEXT DBCONTEXT_TYPE INFRA_PROJECT STARTUP_PROJECT SELECTED_ENV; do
|
|
26
|
+
eval VAR_VALUE=\$$VAR_NAME
|
|
27
|
+
if [ -z "$VAR_VALUE" ]; then
|
|
28
|
+
echo "ERROR: Required variable $VAR_NAME is not set"
|
|
29
|
+
echo "Run step-00-init first"
|
|
30
|
+
exit 1
|
|
31
|
+
fi
|
|
32
|
+
done
|
|
33
|
+
```
|
|
34
|
+
|
|
21
35
|
### 1. Display Configuration
|
|
22
36
|
|
|
23
37
|
```bash
|
|
@@ -16,6 +16,20 @@ Search for existing migrations for this branch and decide whether to recreate or
|
|
|
16
16
|
|
|
17
17
|
## EXECUTION SEQUENCE:
|
|
18
18
|
|
|
19
|
+
### 0. Validate Required Variables
|
|
20
|
+
|
|
21
|
+
```bash
|
|
22
|
+
# Validate required variables from step-00-init
|
|
23
|
+
for VAR_NAME in DBCONTEXT DBCONTEXT_TYPE MIGRATIONS_DIR INFRA_PROJECT STARTUP_PROJECT CURRENT_BRANCH BRANCH_TYPE; do
|
|
24
|
+
eval VAR_VALUE=\$$VAR_NAME
|
|
25
|
+
if [ -z "$VAR_VALUE" ]; then
|
|
26
|
+
echo "ERROR: Required variable $VAR_NAME is not set"
|
|
27
|
+
echo "Run step-00-init first"
|
|
28
|
+
exit 1
|
|
29
|
+
fi
|
|
30
|
+
done
|
|
31
|
+
```
|
|
32
|
+
|
|
19
33
|
### 1. Build Search Pattern
|
|
20
34
|
|
|
21
35
|
```bash
|
|
@@ -42,13 +56,19 @@ echo " Pattern: *${BRANCH_SHORT}*"
|
|
|
42
56
|
### 2. Find Existing Migrations
|
|
43
57
|
|
|
44
58
|
```bash
|
|
45
|
-
#
|
|
46
|
-
|
|
47
|
-
|
|
59
|
+
# Sanitize branch name: only allow alphanumeric, underscore (prevent regex/shell injection)
|
|
60
|
+
BRANCH_SHORT_SAFE=$(echo "$BRANCH_SHORT" | sed 's/[^a-zA-Z0-9_]//g')
|
|
61
|
+
if [ -z "$BRANCH_SHORT_SAFE" ]; then
|
|
62
|
+
echo "ERROR: Invalid branch name (no alphanumeric characters after sanitization)"
|
|
63
|
+
exit 1
|
|
64
|
+
fi
|
|
65
|
+
|
|
66
|
+
# Search for migrations matching this branch (-F = fixed-string, prevents regex injection)
|
|
67
|
+
EXISTING_MIGRATIONS=$(find "$MIGRATIONS_DIR" -name "*.cs" ! -name "*Designer.cs" ! -name "*Snapshot.cs" -type f 2>/dev/null | \
|
|
48
68
|
xargs -I{} basename {} | \
|
|
49
|
-
grep -
|
|
69
|
+
grep -iF "$BRANCH_SHORT_SAFE" || echo "")
|
|
50
70
|
|
|
51
|
-
EXISTING_COUNT=$(echo "$EXISTING_MIGRATIONS" | grep -c "
|
|
71
|
+
EXISTING_COUNT=$(echo "$EXISTING_MIGRATIONS" | grep -c "^[^ ]" 2>/dev/null || echo "0")
|
|
52
72
|
|
|
53
73
|
echo ""
|
|
54
74
|
if [ "$EXISTING_COUNT" -gt 0 ]; then
|
|
@@ -107,6 +127,12 @@ if [ "$ACTION" = "recreate" ]; then
|
|
|
107
127
|
rm -f "$MIGRATIONS_DIR/${mig_name}.cs"
|
|
108
128
|
rm -f "$MIGRATIONS_DIR/${mig_name}.Designer.cs"
|
|
109
129
|
|
|
130
|
+
# Verify deletion succeeded
|
|
131
|
+
if [ -f "$MIGRATIONS_DIR/${mig_name}.cs" ]; then
|
|
132
|
+
echo " ERROR: Failed to delete ${mig_name}.cs"
|
|
133
|
+
exit 1
|
|
134
|
+
fi
|
|
135
|
+
|
|
110
136
|
echo " Removed: $mig_name"
|
|
111
137
|
done
|
|
112
138
|
|
|
@@ -48,7 +48,23 @@ echo ""
|
|
|
48
48
|
echo "Description: $DESCRIPTION"
|
|
49
49
|
```
|
|
50
50
|
|
|
51
|
-
### 2.
|
|
51
|
+
### 2. Verify MCP Availability
|
|
52
|
+
|
|
53
|
+
```bash
|
|
54
|
+
# Check MCP cache before calling suggest_migration
|
|
55
|
+
MCP_STATUS_FILE=".claude/mcp-status.json"
|
|
56
|
+
|
|
57
|
+
if [ -f "$MCP_STATUS_FILE" ]; then
|
|
58
|
+
MCP_STATUS=$(cat "$MCP_STATUS_FILE" | grep -o '"status":"[^"]*"' | head -1 | cut -d'"' -f4)
|
|
59
|
+
if [ "$MCP_STATUS" = "error" ]; then
|
|
60
|
+
echo "ERROR: MCP server is unavailable (status: error)"
|
|
61
|
+
echo "Run: /mcp healthcheck to diagnose"
|
|
62
|
+
exit 1
|
|
63
|
+
fi
|
|
64
|
+
fi
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
### 3. Call MCP for Migration Name (MANDATORY)
|
|
52
68
|
|
|
53
69
|
```javascript
|
|
54
70
|
// DESCRIPTION = from user input (e.g., "Add User Roles")
|
|
@@ -68,7 +84,7 @@ MIGRATION_NAME = result.migrationName;
|
|
|
68
84
|
- Hardcoding context as "core"
|
|
69
85
|
- Using wrong version format
|
|
70
86
|
|
|
71
|
-
###
|
|
87
|
+
### 4. Display Migration Name
|
|
72
88
|
|
|
73
89
|
```bash
|
|
74
90
|
echo ""
|
|
@@ -77,7 +93,7 @@ echo "Context: $DBCONTEXT"
|
|
|
77
93
|
echo ""
|
|
78
94
|
```
|
|
79
95
|
|
|
80
|
-
###
|
|
96
|
+
### 5. Create Migration
|
|
81
97
|
|
|
82
98
|
```bash
|
|
83
99
|
echo "Creating migration..."
|
|
@@ -91,7 +107,7 @@ dotnet ef migrations add "$MIGRATION_NAME" \
|
|
|
91
107
|
--verbose
|
|
92
108
|
```
|
|
93
109
|
|
|
94
|
-
###
|
|
110
|
+
### 6. Verify Creation
|
|
95
111
|
|
|
96
112
|
```bash
|
|
97
113
|
# Check files were created
|
|
@@ -87,6 +87,66 @@ echo " $MIGRATION_FILE"
|
|
|
87
87
|
echo " $DESIGNER_FILE"
|
|
88
88
|
```
|
|
89
89
|
|
|
90
|
+
### 5. Inject SQL Objects (Functions, Views, SP)
|
|
91
|
+
|
|
92
|
+
EF Core does NOT generate DDL for TVF, views, and stored procedures.
|
|
93
|
+
SQL source scripts are in `Persistence/SqlObjects/` (Embedded Resources).
|
|
94
|
+
After a rebase-snapshot, they must be re-injected into the consolidated migration.
|
|
95
|
+
|
|
96
|
+
```bash
|
|
97
|
+
# Check if SqlObjects folder exists with .sql files
|
|
98
|
+
SQL_OBJECTS_DIR="$INFRA_PROJECT_DIR/Persistence/SqlObjects"
|
|
99
|
+
SQL_FILES=$(find "$SQL_OBJECTS_DIR" -name "*.sql" 2>/dev/null | wc -l)
|
|
100
|
+
|
|
101
|
+
if [ "$SQL_FILES" -gt 0 ]; then
|
|
102
|
+
echo ""
|
|
103
|
+
echo "Found $SQL_FILES SQL object(s) in SqlObjects/"
|
|
104
|
+
echo "Injecting SqlObjectHelper.ApplyAll(migrationBuilder) into migration..."
|
|
105
|
+
|
|
106
|
+
# Validate migration file path before sed operations
|
|
107
|
+
if [ ! -f "$MIGRATION_FILE" ]; then
|
|
108
|
+
echo "ERROR: Migration file not found: $MIGRATION_FILE"
|
|
109
|
+
exit 1
|
|
110
|
+
fi
|
|
111
|
+
if ! echo "$MIGRATION_FILE" | grep -qE '\.cs$'; then
|
|
112
|
+
echo "ERROR: Invalid migration file path (not .cs): $MIGRATION_FILE"
|
|
113
|
+
exit 1
|
|
114
|
+
fi
|
|
115
|
+
|
|
116
|
+
# Add using directive if not present
|
|
117
|
+
if ! grep -q "using SmartStack.Infrastructure.Persistence.SqlObjects;" "$MIGRATION_FILE"; then
|
|
118
|
+
sed -i '1s/^/using SmartStack.Infrastructure.Persistence.SqlObjects;\n/' "$MIGRATION_FILE"
|
|
119
|
+
fi
|
|
120
|
+
|
|
121
|
+
# Add SqlObjectHelper.ApplyAll at the end of Up() method
|
|
122
|
+
sed -i '/protected override void Up/,/^ }/ {
|
|
123
|
+
/^ }/ i\
|
|
124
|
+
\ // Apply SQL objects (TVF, Views, SP) from embedded resources\
|
|
125
|
+
\ SqlObjectHelper.ApplyAll(migrationBuilder);
|
|
126
|
+
}' "$MIGRATION_FILE"
|
|
127
|
+
|
|
128
|
+
# Verify injection succeeded (fallback to manual step if sed pattern didn't match)
|
|
129
|
+
if ! grep -q "SqlObjectHelper.ApplyAll" "$MIGRATION_FILE"; then
|
|
130
|
+
echo "WARNING: Automatic injection failed (indentation pattern may differ)"
|
|
131
|
+
echo ""
|
|
132
|
+
echo "MANUAL STEP REQUIRED: Add these lines inside the Up() method before the closing brace:"
|
|
133
|
+
echo ' using SmartStack.Infrastructure.Persistence.SqlObjects;'
|
|
134
|
+
echo ' ...'
|
|
135
|
+
echo ' SqlObjectHelper.ApplyAll(migrationBuilder);'
|
|
136
|
+
echo ""
|
|
137
|
+
echo "File: $MIGRATION_FILE"
|
|
138
|
+
else
|
|
139
|
+
echo " SqlObjectHelper.ApplyAll(migrationBuilder) injected"
|
|
140
|
+
fi
|
|
141
|
+
find "$SQL_OBJECTS_DIR" -name "*.sql" -exec basename {} \; | while read f; do
|
|
142
|
+
echo " - $f"
|
|
143
|
+
done
|
|
144
|
+
else
|
|
145
|
+
echo ""
|
|
146
|
+
echo "No SQL objects found in SqlObjects/ - skipping injection"
|
|
147
|
+
fi
|
|
148
|
+
```
|
|
149
|
+
|
|
90
150
|
---
|
|
91
151
|
|
|
92
152
|
## STATE OUTPUT:
|
|
@@ -56,8 +56,10 @@ detect_dbcontext() {
|
|
|
56
56
|
return
|
|
57
57
|
fi
|
|
58
58
|
|
|
59
|
-
# Priority 2: Client with SmartStack NuGet → BOTH contexts
|
|
60
|
-
|
|
59
|
+
# Priority 2: Client project with SmartStack NuGet → BOTH contexts
|
|
60
|
+
# Detect: csproj files that have a PackageReference to SmartStack (not ProjectReference)
|
|
61
|
+
# This identifies client projects created via `ss init` that consume SmartStack as NuGet
|
|
62
|
+
if find . -name "*.csproj" -exec grep -ql "PackageReference.*SmartStack" {} \; 2>/dev/null; then
|
|
61
63
|
DBCONTEXT="CoreDbContext"
|
|
62
64
|
DBCONTEXT_TYPE="both"
|
|
63
65
|
SCHEMA="core"
|
|
@@ -197,20 +199,57 @@ determine_base_branch() {
|
|
|
197
199
|
|
|
198
200
|
```bash
|
|
199
201
|
block_production() {
|
|
200
|
-
# Check for production indicators
|
|
201
|
-
if grep -
|
|
202
|
-
echo "BLOCKED: Production environment detected"
|
|
202
|
+
# Check for production indicators (case-insensitive)
|
|
203
|
+
if grep -qi '"Production"' "$CONFIG_FILE" 2>/dev/null; then
|
|
204
|
+
echo "BLOCKED: Production environment detected in $CONFIG_FILE"
|
|
203
205
|
exit 1
|
|
204
206
|
fi
|
|
205
207
|
|
|
206
|
-
|
|
207
|
-
|
|
208
|
+
# Case-insensitive database name check
|
|
209
|
+
DB_LOWER=$(echo "$DATABASE_NAME" | tr '[:upper:]' '[:lower:]')
|
|
210
|
+
if [[ "$DB_LOWER" == *"prod"* ]] || [[ "$DB_LOWER" == *"production"* ]]; then
|
|
211
|
+
echo "BLOCKED: Production database detected ($DATABASE_NAME)"
|
|
208
212
|
exit 1
|
|
209
213
|
fi
|
|
214
|
+
|
|
215
|
+
# Environment name check (case-insensitive)
|
|
216
|
+
ENV_LOWER=$(echo "$SELECTED_ENV" | tr '[:upper:]' '[:lower:]')
|
|
217
|
+
if [[ "$ENV_LOWER" == "production" ]] || [[ "$ENV_LOWER" == "prod" ]]; then
|
|
218
|
+
echo "BLOCKED: Production environment selected ($SELECTED_ENV)"
|
|
219
|
+
exit 1
|
|
220
|
+
fi
|
|
221
|
+
}
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
### 7. Dual Context Helper
|
|
225
|
+
|
|
226
|
+
```bash
|
|
227
|
+
# Helper for steps that need to run for both contexts when RUN_BOTH=true
|
|
228
|
+
# Usage: run_for_contexts "command_or_function"
|
|
229
|
+
# Executes with CoreDbContext first, then ExtensionsDbContext
|
|
230
|
+
# Maintains deploy order constraint: Core MUST run first
|
|
231
|
+
|
|
232
|
+
run_for_contexts() {
|
|
233
|
+
if [ "$RUN_BOTH" = "true" ]; then
|
|
234
|
+
echo "=== Running for CoreDbContext (core schema) ==="
|
|
235
|
+
DBCONTEXT="CoreDbContext"
|
|
236
|
+
DBCONTEXT_TYPE="core"
|
|
237
|
+
SCHEMA="core"
|
|
238
|
+
eval "$1"
|
|
239
|
+
|
|
240
|
+
echo ""
|
|
241
|
+
echo "=== Running for ExtensionsDbContext (extensions schema) ==="
|
|
242
|
+
DBCONTEXT="ExtensionsDbContext"
|
|
243
|
+
DBCONTEXT_TYPE="extensions"
|
|
244
|
+
SCHEMA="extensions"
|
|
245
|
+
eval "$1"
|
|
246
|
+
else
|
|
247
|
+
eval "$1"
|
|
248
|
+
fi
|
|
210
249
|
}
|
|
211
250
|
```
|
|
212
251
|
|
|
213
|
-
###
|
|
252
|
+
### 8. Display Summary
|
|
214
253
|
|
|
215
254
|
```
|
|
216
255
|
EF CORE CONTEXT
|
|
@@ -133,9 +133,9 @@ echo " Down methods: $DOWN_METHODS"
|
|
|
133
133
|
|
|
134
134
|
### 6. Inject SQL Objects (Functions, Views, SP)
|
|
135
135
|
|
|
136
|
-
EF Core
|
|
137
|
-
|
|
138
|
-
|
|
136
|
+
EF Core does NOT generate DDL for TVF, views, and stored procedures.
|
|
137
|
+
SQL source scripts are in `Persistence/SqlObjects/` (Embedded Resources).
|
|
138
|
+
After a squash, they must be re-injected into the consolidated migration.
|
|
139
139
|
|
|
140
140
|
```bash
|
|
141
141
|
# Check if SqlObjects folder exists with .sql files
|
|
@@ -147,6 +147,16 @@ if [ "$SQL_FILES" -gt 0 ]; then
|
|
|
147
147
|
echo "Found $SQL_FILES SQL object(s) in SqlObjects/"
|
|
148
148
|
echo "Injecting SqlObjectHelper.ApplyAll(migrationBuilder) into migration..."
|
|
149
149
|
|
|
150
|
+
# Validate migration file path before sed operations (prevent path injection)
|
|
151
|
+
if [ ! -f "$MIGRATION_FILE" ]; then
|
|
152
|
+
echo "ERROR: Migration file not found: $MIGRATION_FILE"
|
|
153
|
+
exit 1
|
|
154
|
+
fi
|
|
155
|
+
if ! echo "$MIGRATION_FILE" | grep -qE '\.cs$'; then
|
|
156
|
+
echo "ERROR: Invalid migration file path (not .cs): $MIGRATION_FILE"
|
|
157
|
+
exit 1
|
|
158
|
+
fi
|
|
159
|
+
|
|
150
160
|
# Add using directive if not present
|
|
151
161
|
if ! grep -q "using SmartStack.Infrastructure.Persistence.SqlObjects;" "$MIGRATION_FILE"; then
|
|
152
162
|
sed -i '1s/^/using SmartStack.Infrastructure.Persistence.SqlObjects;\n/' "$MIGRATION_FILE"
|
|
@@ -160,9 +170,21 @@ if [ "$SQL_FILES" -gt 0 ]; then
|
|
|
160
170
|
\ SqlObjectHelper.ApplyAll(migrationBuilder);
|
|
161
171
|
}' "$MIGRATION_FILE"
|
|
162
172
|
|
|
163
|
-
|
|
173
|
+
# Verify injection succeeded (fallback to manual step if sed pattern didn't match)
|
|
174
|
+
if ! grep -q "SqlObjectHelper.ApplyAll" "$MIGRATION_FILE"; then
|
|
175
|
+
echo "WARNING: Automatic injection failed (indentation pattern may differ)"
|
|
176
|
+
echo ""
|
|
177
|
+
echo "MANUAL STEP REQUIRED: Add these lines inside the Up() method before the closing brace:"
|
|
178
|
+
echo ' using SmartStack.Infrastructure.Persistence.SqlObjects;'
|
|
179
|
+
echo ' ...'
|
|
180
|
+
echo ' SqlObjectHelper.ApplyAll(migrationBuilder);'
|
|
181
|
+
echo ""
|
|
182
|
+
echo "File: $MIGRATION_FILE"
|
|
183
|
+
else
|
|
184
|
+
echo " SqlObjectHelper.ApplyAll(migrationBuilder) injected"
|
|
185
|
+
fi
|
|
164
186
|
find "$SQL_OBJECTS_DIR" -name "*.sql" -exec basename {} \; | while read f; do
|
|
165
|
-
echo "
|
|
187
|
+
echo " - $f"
|
|
166
188
|
done
|
|
167
189
|
else
|
|
168
190
|
echo ""
|
|
@@ -65,13 +65,15 @@ Execute GitFlow workflows with automatic versioning, worktree management, and EF
|
|
|
65
65
|
| Short | Long | Description |
|
|
66
66
|
|-------|------|-------------|
|
|
67
67
|
| `-A` | `--no-auto` | Disable auto mode |
|
|
68
|
+
| `--ws` | `--workspace` | Batch init: initialize all repos in a workspace |
|
|
68
69
|
</flags>
|
|
69
70
|
|
|
70
71
|
<actions>
|
|
71
72
|
**Primary actions:**
|
|
72
73
|
| Action | Description | Step |
|
|
73
74
|
|--------|-------------|------|
|
|
74
|
-
| `init` | Initialize GitFlow config | step-init |
|
|
75
|
+
| `init` | Initialize GitFlow config (orchestrates detect→clone→validate) | step-init |
|
|
76
|
+
| `init --workspace` | Batch initialize all repos in a workspace | step-init |
|
|
75
77
|
| `start` | Create new branch + worktree | step-start |
|
|
76
78
|
| `commit` | Commit with EF Core validation | step-commit |
|
|
77
79
|
| `sync` | Sync + rebase with remote | step-sync |
|
|
@@ -178,25 +180,30 @@ start ──► commit* ──► sync ──► pr ──► merge ──► fi
|
|
|
178
180
|
**ROUTING LOGIC:**
|
|
179
181
|
|
|
180
182
|
1. Parse flags and action from input
|
|
181
|
-
2. Route to appropriate step or
|
|
182
|
-
|
|
183
|
-
| Input Pattern |
|
|
184
|
-
|
|
185
|
-
| `init` | `steps/step-init.md` |
|
|
186
|
-
| `start
|
|
187
|
-
|
|
|
188
|
-
|
|
|
189
|
-
|
|
|
190
|
-
| `
|
|
191
|
-
| `
|
|
192
|
-
| `
|
|
193
|
-
| `
|
|
194
|
-
| `
|
|
195
|
-
| `
|
|
196
|
-
|
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
183
|
+
2. Route to appropriate step or Task agent:
|
|
184
|
+
|
|
185
|
+
| Input Pattern | Step File | Task Agent (`subagent_type`) |
|
|
186
|
+
|---------------|-----------|----------------------------|
|
|
187
|
+
| `init` | `steps/step-init.md` | `gitflow-init` |
|
|
188
|
+
| `start`, `-f`, `-r`, `-h` | `steps/step-start.md` | `gitflow-start` |
|
|
189
|
+
| `commit [msg]` | `steps/step-commit.md` | `gitflow-commit` |
|
|
190
|
+
| `sync` | `steps/step-sync.md` | — |
|
|
191
|
+
| `plan` | `steps/step-plan.md` | `gitflow-plan` |
|
|
192
|
+
| `pr` | `steps/step-pr.md` | `gitflow-pr` |
|
|
193
|
+
| `merge` | `steps/step-merge.md` | `gitflow-merge` |
|
|
194
|
+
| `finish` | `steps/step-finish.md` | `gitflow-finish` |
|
|
195
|
+
| `status`, `-s` | `phases/status.md` | `gitflow-status` |
|
|
196
|
+
| `abort` | `phases/abort.md` | `gitflow-abort` |
|
|
197
|
+
| `cleanup` | `phases/cleanup.md` | `gitflow-cleanup` |
|
|
198
|
+
| (no action, on feature/*) | `steps/step-commit.md` | `gitflow-commit` |
|
|
199
|
+
|
|
200
|
+
**Execution mode:**
|
|
201
|
+
|
|
202
|
+
| Mode | How to route |
|
|
203
|
+
|------|-------------|
|
|
204
|
+
| **Single step** (no `-a`) | Read the step file and execute inline |
|
|
205
|
+
| **Auto mode** (`-a`) | Use `Task` tool with the matching `subagent_type` for each step sequentially |
|
|
206
|
+
| **Standalone phases** | Always delegate to Task agent (fast, isolated) |
|
|
200
207
|
|
|
201
208
|
</entry_point>
|
|
202
209
|
|
|
@@ -253,12 +260,67 @@ start ──► commit* ──► sync ──► pr ──► merge ──► fi
|
|
|
253
260
|
| release | as specified | 1.2.0 → 2.0.0 |
|
|
254
261
|
</versioning>
|
|
255
262
|
|
|
263
|
+
<task_agents>
|
|
264
|
+
|
|
265
|
+
**Task agent delegation (Opus 4.6):**
|
|
266
|
+
|
|
267
|
+
Each action has a matching Task agent that can execute independently. Use `Task` tool with the `subagent_type` parameter to delegate:
|
|
268
|
+
|
|
269
|
+
| Agent | Model | Tools | Use for |
|
|
270
|
+
|-------|-------|-------|---------|
|
|
271
|
+
| `gitflow-commit` | haiku | Bash, Read, Glob, Grep | Fast commit + EF Core validation |
|
|
272
|
+
| `gitflow-pr` | haiku | Bash, Glob | Fast PR creation |
|
|
273
|
+
| `gitflow-status` | haiku | Bash, Read, Glob | Fast status check |
|
|
274
|
+
| `gitflow-review` | haiku | Bash, Glob, Read | Fast PR review |
|
|
275
|
+
| `gitflow-start` | sonnet | Bash, Read, Glob, Write | Branch + worktree creation |
|
|
276
|
+
| `gitflow-merge` | sonnet | Bash, Read, Glob, Grep, Edit | Safe merge with validation |
|
|
277
|
+
| `gitflow-finish` | sonnet | Bash, Read, Glob, Write | Tag + cleanup + merge-back |
|
|
278
|
+
| `gitflow-plan` | sonnet | Bash, Read, Glob, Grep, Write | Integration planning |
|
|
279
|
+
| `gitflow-exec` | sonnet | Bash, Read, Glob, Grep, Edit, Write | Plan execution |
|
|
280
|
+
| `gitflow-init` | sonnet | Bash, Read, Write, Glob, AskUserQuestion | Project setup (orchestrator) |
|
|
281
|
+
| `gitflow-init-detect` | haiku | Bash, Read | Environment detection (sub-agent) |
|
|
282
|
+
| `gitflow-init-clone` | sonnet | Bash, Read, Write | Bare clone + worktrees (sub-agent) |
|
|
283
|
+
| `gitflow-init-validate` | haiku | Bash, Read, Glob | Post-init verification + repair (sub-agent) |
|
|
284
|
+
| `gitflow-cleanup` | sonnet | Bash, Read, Glob, Write | Orphan worktree audit |
|
|
285
|
+
| `gitflow-abort` | sonnet | Bash, Read, Glob, Write | Rollback/recovery |
|
|
286
|
+
|
|
287
|
+
**Init team delegation (orchestrated by `gitflow-init`):**
|
|
288
|
+
|
|
289
|
+
| Step | Sub-agent | Model | Purpose |
|
|
290
|
+
|------|-----------|-------|---------|
|
|
291
|
+
| 1 | `gitflow-init-detect` | haiku | Platform, workspace, git state detection |
|
|
292
|
+
| 2 | (orchestrator) | sonnet | AskUserQuestion for URL, path, name |
|
|
293
|
+
| 3 | `gitflow-init-clone` | sonnet | Bare clone + worktree creation (zero `cd`, absolute paths) |
|
|
294
|
+
| 4 | (orchestrator) | sonnet | Write config.json v2.1.0 |
|
|
295
|
+
| 5 | `gitflow-init-validate` | haiku | Verify structure + auto-repair |
|
|
296
|
+
|
|
297
|
+
**Parallel execution opportunities:**
|
|
298
|
+
|
|
299
|
+
| Scenario | Parallel agents |
|
|
300
|
+
|----------|----------------|
|
|
301
|
+
| Status check | `gitflow-status` in background while user continues |
|
|
302
|
+
| Pre-PR validation | Build check + migration check in parallel Bash calls |
|
|
303
|
+
| Auto release | Sequential: start → commit → pr → (wait) → finish |
|
|
304
|
+
| Workspace init | Sequential per repo, but detection is parallel |
|
|
305
|
+
|
|
306
|
+
**Agent prompt template:**
|
|
307
|
+
```
|
|
308
|
+
Execute {action} for GitFlow.
|
|
309
|
+
Working directory: {worktree_path}
|
|
310
|
+
Branch: {branch_name} ({branch_type})
|
|
311
|
+
Target: {base_branch}
|
|
312
|
+
Provider: {git_provider}
|
|
313
|
+
Version: {version_current}
|
|
314
|
+
Auto mode: {auto_mode}
|
|
315
|
+
```
|
|
316
|
+
|
|
317
|
+
</task_agents>
|
|
318
|
+
|
|
256
319
|
<execution_rules>
|
|
257
320
|
|
|
258
|
-
- **
|
|
259
|
-
- **
|
|
260
|
-
- **
|
|
261
|
-
- **Follow next_step directive** at end of each step
|
|
321
|
+
- **Single step mode**: Read the step file and execute inline
|
|
322
|
+
- **Auto mode (`-a`)**: Delegate each step to its Task agent sequentially
|
|
323
|
+
- **Standalone phases**: Always delegate to Task agent (fast, isolated)
|
|
262
324
|
- **NEVER skip EF Core validation** - migrations are critical
|
|
263
325
|
- **Safety > Correctness > Speed**
|
|
264
326
|
|
|
@@ -267,14 +329,14 @@ start ──► commit* ──► sync ──► pr ──► merge ──► fi
|
|
|
267
329
|
| Mode | Behavior |
|
|
268
330
|
|------|----------|
|
|
269
331
|
| **Without `-a`** | Execute ONLY the requested step, then **STOP and wait for user** |
|
|
270
|
-
| **With `-a`** | Execute ALL steps automatically
|
|
332
|
+
| **With `-a`** | Execute ALL steps automatically via Task agent delegation |
|
|
271
333
|
|
|
272
334
|
**Examples:**
|
|
273
335
|
```bash
|
|
274
|
-
/gitflow -r 1.20.0 #
|
|
275
|
-
/gitflow -r -a 1.20.0 #
|
|
276
|
-
/gitflow -f my-feature #
|
|
277
|
-
/gitflow
|
|
336
|
+
/gitflow -r 1.20.0 # Reads step-start.md, executes inline → STOPS
|
|
337
|
+
/gitflow -r -a 1.20.0 # Delegates to gitflow-start → gitflow-pr → gitflow-finish
|
|
338
|
+
/gitflow -f my-feature # Reads step-start.md, executes inline → STOPS
|
|
339
|
+
/gitflow commit # Reads step-commit.md, executes inline → STOPS
|
|
278
340
|
```
|
|
279
341
|
|
|
280
342
|
**NEVER chain steps automatically without `-a` flag. The user decides the pace.**
|