@polymorphism-tech/morph-spec 9.7.0 → 10.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/CLAUDE.md +11 -11
- package/README.md +4 -4
- package/bin/morph-spec.js +41 -44
- package/claude-plugin.json +1 -1
- package/docs/CHEATSHEET.md +1 -1
- package/docs/QUICKSTART.md +1 -1
- package/framework/CLAUDE.md +24 -30
- package/framework/MORPH.md +47 -123
- package/framework/agents.json +6 -374
- package/framework/commands/morph-apply.md +1 -1
- package/framework/commands/morph-archive.md +4 -3
- package/framework/commands/morph-hotfix.md +8 -30
- package/framework/commands/morph-infra.md +2 -2
- package/framework/commands/morph-media.md +10 -9
- package/framework/commands/morph-review.md +15 -0
- package/framework/commands/morph-status.md +1 -1
- package/framework/docs/CLI.md +100 -102
- package/framework/evals/review-checklist.md +46 -54
- package/framework/hooks/README.md +4 -4
- package/framework/hooks/claude-code/__pycache__/statusline.cpython-313.pyc +0 -0
- package/framework/hooks/claude-code/core/README.md +1 -1
- package/framework/hooks/claude-code/core/denylist.json +4 -4
- package/framework/hooks/claude-code/core/gate-guard.js +9 -0
- package/framework/hooks/claude-code/core/masked-exit.js +49 -0
- package/framework/hooks/claude-code/core/state-sync.js +4 -1
- package/framework/hooks/claude-code/core/telemetry-log.js +1 -2
- package/framework/hooks/claude-code/core/test-budget.js +10 -70
- package/framework/hooks/claude-code/core/validate-completion.js +11 -24
- package/framework/hooks/claude-code/core/worktree-context.js +5 -22
- package/framework/hooks/claude-code/core/worktree-create.js +6 -45
- package/framework/hooks/claude-code/core/worktree-env-inject.js +2 -10
- package/framework/hooks/shared/e2e-check.js +0 -0
- package/framework/hooks/shared/gate-event.js +2 -2
- package/framework/hooks/shared/graph-refresh.js +20 -3
- package/framework/hooks/shared/heavy-command.js +32 -1
- package/framework/hooks/shared/heavy-config.js +1 -1
- package/framework/hooks/shared/heavy-slots.js +41 -4
- package/framework/hooks/shared/next-step.js +63 -24
- package/framework/hooks/shared/phase-utils.js +6 -9
- package/framework/hooks/shared/report-progress.js +86 -0
- package/framework/hooks/shared/state-reader.js +3 -2
- package/framework/hooks/statusline.js +332 -0
- package/framework/phases.json +32 -10
- package/framework/rules/ai-agents-standards.md +9 -1
- package/framework/rules/csharp-standards.md +4 -0
- package/framework/rules/ef-standards.md +20 -0
- package/framework/rules/frontend-standards.md +1 -1
- package/framework/rules/implement-report.md +25 -0
- package/framework/rules/infrastructure-standards.md +2 -0
- package/framework/rules/nextjs-standards.md +7 -0
- package/framework/rules/plan-grammar.md +53 -0
- package/framework/rules/ui-design.md +27 -0
- package/framework/schemas/config.schema.json +12 -19
- package/framework/schemas/feature.schema.json +7 -1
- package/framework/skills/core/create-umbraco-lp/SKILL.md +1 -1
- package/framework/skills/core/create-umbraco-lp/references/umbraco-lp-patterns.md +1 -1
- package/framework/skills/core/migrate-lp-to-umbraco/SKILL.md +2 -2
- package/framework/skills/core/morph-apply/SKILL.md +38 -166
- package/framework/skills/core/morph-apply/references/debugging.md +8 -0
- package/framework/skills/core/morph-apply/references/hotfix.md +42 -0
- package/framework/skills/core/morph-apply/references/machine.md +29 -0
- package/framework/skills/core/{morph-media/SKILL.md → morph-apply/references/media.md} +11 -74
- package/framework/skills/core/morph-apply/references/review.md +65 -0
- package/framework/skills/core/morph-plan/SKILL.md +42 -108
- package/framework/skills/core/morph-plan/references/critique.md +40 -0
- package/framework/skills/core/morph-plan/references/interview.md +25 -0
- package/framework/skills/core/morph-uiux/SKILL.md +47 -64
- package/framework/skills/core/morph-uiux/surfaces.json +32 -0
- package/framework/standards/STANDARDS.json +32 -5
- package/framework/standards/STANDARDS.meta.json +5 -1
- package/framework/standards/ai-agents/agent-session.md +2 -3
- package/framework/standards/ai-agents/context-providers.md +2 -2
- package/framework/standards/ai-agents/durable-workflows-hitl.md +2 -2
- package/framework/standards/ai-agents/providers/model-registry.md +2 -2
- package/framework/standards/ai-agents/rag-custom-pgvector.md +6 -6
- package/framework/standards/ai-agents/setup.md +1 -1
- package/framework/standards/ai-agents/tool-adapters.md +2 -2
- package/framework/standards/architecture/stack-baseline.md +47 -0
- package/framework/standards/backend/integrations/neon-auth/neon-auth.md +2 -4
- package/framework/standards/frontend/design-system/ai-image-generation.md +51 -12
- package/framework/standards/frontend/design-system/ai-video-generation.md +50 -4
- package/framework/standards/frontend/design-system/art-direction.md +2 -2
- package/framework/standards/frontend/scroll-driven/frame-scrub.md +12 -2
- package/framework/standards/frontend/scroll-driven/scroll-components.md +76 -4
- package/framework/templates/.idea/morph-templates.xml +92 -0
- package/framework/templates/.vscode/morph-templates.code-snippets +186 -0
- package/framework/templates/IDE-SNIPPETS.md +262 -262
- package/framework/templates/REGISTRY.json +1 -2
- package/framework/templates/code/dotnet/abstractions/api-endpoint.cs +7 -7
- package/framework/templates/code/dotnet/feature/request.cs.hbs +4 -4
- package/framework/templates/code/dotnet/feature/response.cs.hbs +4 -4
- package/framework/templates/code/sql/ai-agents/pgvector-embeddings-migration.sql.template +91 -91
- package/framework/templates/context/ARCHITECTURE.md +1 -1
- package/framework/templates/docs/plan.md +12 -12
- package/framework/templates/docs/ui-mockups.md +17 -105
- package/framework/templates/frontend/nextjs/client-component.tsx.hbs +26 -26
- package/framework/templates/frontend/nextjs/tsconfig.json.hbs +26 -26
- package/framework/templates/infrastructure/docker/Dockerfile.template +58 -58
- package/framework/templates/infrastructure/docker/dockerfile-api.dockerfile +38 -38
- package/framework/templates/infrastructure/docker/dockerfile-web.dockerfile +48 -48
- package/framework/templates/infrastructure/github/actions/docker-build-push/action.yml.hbs +45 -45
- package/framework/templates/infrastructure/github/actions/health-check/action.yml.hbs +27 -27
- package/framework/templates/infrastructure/github/workflows/docker-build-push.yml.hbs +59 -59
- package/framework/templates/infrastructure/github/workflows/dotnet-build.yml.hbs +39 -39
- package/framework/templates/state.template.json +17 -17
- package/framework/templates/ui/design-system.css +226 -226
- package/package.json +1 -1
- package/src/commands/e2e/e2e.js +88 -23
- package/src/commands/graph/diff.js +74 -0
- package/src/commands/graph/status.js +1 -1
- package/src/commands/observability/cost.js +2 -4
- package/src/commands/observability/telemetry.js +1 -1
- package/src/commands/project/doctor.js +23 -39
- package/src/commands/project/fleet.js +5 -6
- package/src/commands/project/init.js +63 -36
- package/src/commands/project/stack-scan.js +3 -42
- package/src/commands/project/stack-set.js +26 -0
- package/src/commands/project/status.js +12 -13
- package/src/commands/project/update.js +39 -3
- package/src/commands/project/worktree.js +27 -16
- package/src/commands/state/advance.js +17 -17
- package/src/commands/state/approve.js +0 -6
- package/src/commands/state/archive.js +27 -1
- package/src/commands/state/auto-approval.js +1 -1
- package/src/commands/state/create.js +0 -5
- package/src/commands/state/finish.js +43 -1
- package/src/commands/state/gate-check.js +37 -30
- package/src/commands/state/gate-decision.js +3 -2
- package/src/commands/state/next.js +1 -0
- package/src/commands/state/recap.js +67 -0
- package/src/commands/state/report-check.js +39 -146
- package/src/commands/validation/plan-check.js +16 -11
- package/src/commands/validation/validate-feature.js +3 -3
- package/src/commands/validation/verify.js +6 -6
- package/src/core/paths/output-schema.js +3 -3
- package/src/core/state/state-manager.js +2 -4
- package/src/dashboard/app/components/CommandPalette.jsx +2 -5
- package/src/dashboard/app/components/GatePauses.jsx +116 -0
- package/src/dashboard/app/components/SessionMap.jsx +77 -0
- package/src/dashboard/app/main.jsx +13 -13
- package/src/dashboard/app/pages/Activity.jsx +4 -0
- package/src/dashboard/app/pages/AgentMap.jsx +1 -2
- package/src/dashboard/app/pages/FeatureDetail.jsx +129 -186
- package/src/dashboard/app/pages/Features.jsx +7 -7
- package/src/dashboard/app/pages/PhasePipeline.jsx +1 -1
- package/src/dashboard/app/pages/Portfolio.jsx +40 -5
- package/src/dashboard/scanner/activity-scanner.js +29 -0
- package/src/dashboard/scanner/agents-scanner.js +11 -14
- package/src/dashboard/scanner/features-scanner.js +45 -24
- package/src/dashboard/scanner/project-api.js +11 -2
- package/src/dashboard/scanner/skills-scanner.js +11 -1
- package/src/dashboard/vite.config.js +24 -24
- package/src/lib/e2e/applicability.js +3 -1
- package/src/lib/git/tree-state.js +1 -16
- package/src/lib/graph/diff-tree.js +127 -0
- package/src/lib/graph/graphify-runtime.js +12 -5
- package/src/lib/heavy/gate.js +22 -1
- package/src/lib/installers/memory-installer.js +2 -2
- package/src/lib/installers/rules-installer.js +57 -0
- package/src/lib/installers/stack-assets.js +17 -0
- package/src/lib/installers/stack-sync.js +219 -0
- package/src/lib/plan/checks.js +55 -110
- package/src/lib/plan/critique.js +28 -0
- package/src/lib/plan/media.js +42 -0
- package/src/lib/plan/plan-html.js +125 -0
- package/src/lib/plan/plan-parser.js +34 -45
- package/src/lib/recap/piper.js +36 -0
- package/src/lib/recap/recap.js +232 -0
- package/src/lib/review-reports.js +33 -7
- package/src/lib/risk-detector.js +90 -11
- package/src/lib/specs/screen-checklist.js +33 -48
- package/src/lib/stack/dotnet-build-ignores.js +8 -9
- package/src/lib/tasks/test-nodes.js +24 -6
- package/src/lib/tasks/test-runner.js +40 -1
- package/src/lib/telemetry/metrics.js +27 -29
- package/src/lib/validators/reuse/reuse-validator.js +1 -9
- package/src/lib/validators/verify-runner.js +50 -19
- package/src/lib/worktree/fleet-scanner.js +7 -20
- package/src/lib/worktree/worktree-audit.js +0 -37
- package/src/scripts/setup-infra.js +15 -50
- package/src/utils/agents-installer.js +27 -201
- package/src/utils/hooks-installer.js +11 -95
- package/framework/hooks/claude-code/core/warn-bash-source-write.js +0 -23
- package/framework/hooks/claude-code/statusline.py +0 -699
- package/framework/hooks/claude-code/statusline.sh +0 -11
- package/framework/hooks/shared/agent-reap.js +0 -74
- package/framework/hooks/shared/slice-progress.js +0 -110
- package/framework/skills/core/morph-hotfix/SKILL.md +0 -133
- package/framework/skills/core/morph-machine/SKILL.md +0 -46
- package/framework/skills/core/morph-review/SKILL.md +0 -129
- package/framework/skills/core/morph-standards/SKILL.md +0 -52
- package/framework/standards/PROVENANCE.json +0 -119
- package/src/commands/project/worktree-reap.js +0 -34
- package/src/commands/state/handoff.js +0 -65
- package/src/commands/validation/mutate.js +0 -263
- package/src/commands/validation/scout-check.js +0 -28
- package/src/lib/generators/handoff-generator.js +0 -172
- package/src/lib/mutation/adapters.js +0 -79
- package/src/lib/mutation/commands.js +0 -61
- package/src/lib/mutation/dotnet-introspection.js +0 -281
- package/src/lib/mutation/manifest.js +0 -144
- package/src/lib/mutation/plan.js +0 -44
- package/src/lib/mutation/report.js +0 -68
- package/src/lib/mutation/runner.js +0 -301
- package/src/lib/mutation/schemata.js +0 -60
- package/src/lib/mutation/snapshot.js +0 -65
- package/src/lib/mutation/subset.js +0 -109
- package/src/lib/mutation/trx.js +0 -50
- package/src/lib/scout/scout-check.js +0 -293
- package/src/lib/validators/traceability-check.js +0 -103
- package/src/lib/worktree/agent-reaper.js +0 -247
|
@@ -1,226 +1,226 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Design System - {Project Name}
|
|
3
|
-
*
|
|
4
|
-
* CSS Variables generated from design-system.md
|
|
5
|
-
* Use estas variáveis em todo o projeto para manter consistência visual.
|
|
6
|
-
*
|
|
7
|
-
* Template MORPH-SPEC by Polymorphism Tech
|
|
8
|
-
*/
|
|
9
|
-
|
|
10
|
-
:root {
|
|
11
|
-
/* ========================================
|
|
12
|
-
* CORES PRINCIPAIS
|
|
13
|
-
* ======================================== */
|
|
14
|
-
|
|
15
|
-
--color-primary: #{hex da cor primária};
|
|
16
|
-
--color-primary-hover: #{hex da cor primária mais escura};
|
|
17
|
-
--color-primary-active: #{hex da cor primária ainda mais escura};
|
|
18
|
-
|
|
19
|
-
--color-secondary: #{hex da cor secundária};
|
|
20
|
-
--color-secondary-hover: #{hex};
|
|
21
|
-
--color-secondary-active: #{hex};
|
|
22
|
-
|
|
23
|
-
/* ========================================
|
|
24
|
-
* CORES DE ESTADO
|
|
25
|
-
* ======================================== */
|
|
26
|
-
|
|
27
|
-
--color-success: #{hex};
|
|
28
|
-
--color-success-bg: #{hex com transparência ou shade mais claro};
|
|
29
|
-
--color-success-border: #{hex};
|
|
30
|
-
|
|
31
|
-
--color-error: #{hex};
|
|
32
|
-
--color-error-bg: #{hex};
|
|
33
|
-
--color-error-border: #{hex};
|
|
34
|
-
|
|
35
|
-
--color-warning: #{hex};
|
|
36
|
-
--color-warning-bg: #{hex};
|
|
37
|
-
--color-warning-border: #{hex};
|
|
38
|
-
|
|
39
|
-
--color-info: #{hex};
|
|
40
|
-
--color-info-bg: #{hex};
|
|
41
|
-
--color-info-border: #{hex};
|
|
42
|
-
|
|
43
|
-
/* ========================================
|
|
44
|
-
* ESCALA DE NEUTROS (Cinzas)
|
|
45
|
-
* ======================================== */
|
|
46
|
-
|
|
47
|
-
--color-gray-50: #{hex};
|
|
48
|
-
--color-gray-100: #{hex};
|
|
49
|
-
--color-gray-200: #{hex};
|
|
50
|
-
--color-gray-300: #{hex};
|
|
51
|
-
--color-gray-400: #{hex};
|
|
52
|
-
--color-gray-500: #{hex};
|
|
53
|
-
--color-gray-600: #{hex};
|
|
54
|
-
--color-gray-700: #{hex};
|
|
55
|
-
--color-gray-800: #{hex};
|
|
56
|
-
--color-gray-900: #{hex};
|
|
57
|
-
|
|
58
|
-
/* ========================================
|
|
59
|
-
* TIPOGRAFIA - FONTES
|
|
60
|
-
* ======================================== */
|
|
61
|
-
|
|
62
|
-
--font-sans: '{Font Name}', -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', sans-serif;
|
|
63
|
-
--font-serif: '{Font Name}', Georgia, 'Times New Roman', serif;
|
|
64
|
-
--font-mono: '{Font Name}', 'Fira Code', 'Courier New', Consolas, monospace;
|
|
65
|
-
|
|
66
|
-
/* ========================================
|
|
67
|
-
* TIPOGRAFIA - TAMANHOS
|
|
68
|
-
* ======================================== */
|
|
69
|
-
|
|
70
|
-
--text-xs: 0.75rem; /* 12px */
|
|
71
|
-
--text-sm: 0.875rem; /* 14px */
|
|
72
|
-
--text-base: 1rem; /* 16px */
|
|
73
|
-
--text-lg: 1.125rem; /* 18px */
|
|
74
|
-
--text-xl: 1.25rem; /* 20px */
|
|
75
|
-
--text-2xl: 1.5rem; /* 24px */
|
|
76
|
-
--text-3xl: 1.875rem; /* 30px */
|
|
77
|
-
--text-4xl: 2.25rem; /* 36px */
|
|
78
|
-
--text-5xl: 3rem; /* 48px */
|
|
79
|
-
|
|
80
|
-
/* ========================================
|
|
81
|
-
* TIPOGRAFIA - LINE HEIGHTS
|
|
82
|
-
* ======================================== */
|
|
83
|
-
|
|
84
|
-
--leading-none: 1;
|
|
85
|
-
--leading-tight: 1.25;
|
|
86
|
-
--leading-snug: 1.375;
|
|
87
|
-
--leading-normal: 1.5;
|
|
88
|
-
--leading-relaxed: 1.625;
|
|
89
|
-
--leading-loose: 2;
|
|
90
|
-
|
|
91
|
-
/* ========================================
|
|
92
|
-
* TIPOGRAFIA - FONT WEIGHTS
|
|
93
|
-
* ======================================== */
|
|
94
|
-
|
|
95
|
-
--font-light: 300;
|
|
96
|
-
--font-regular: 400;
|
|
97
|
-
--font-medium: 500;
|
|
98
|
-
--font-semibold: 600;
|
|
99
|
-
--font-bold: 700;
|
|
100
|
-
--font-extrabold: 800;
|
|
101
|
-
|
|
102
|
-
/* ========================================
|
|
103
|
-
* ESPAÇAMENTO
|
|
104
|
-
* Baseado em múltiplos de {base}px (ex: 4px)
|
|
105
|
-
* ======================================== */
|
|
106
|
-
|
|
107
|
-
--space-0: 0;
|
|
108
|
-
--space-1: 0.25rem; /* 4px */
|
|
109
|
-
--space-2: 0.5rem; /* 8px */
|
|
110
|
-
--space-3: 0.75rem; /* 12px */
|
|
111
|
-
--space-4: 1rem; /* 16px */
|
|
112
|
-
--space-5: 1.25rem; /* 20px */
|
|
113
|
-
--space-6: 1.5rem; /* 24px */
|
|
114
|
-
--space-7: 1.75rem; /* 28px */
|
|
115
|
-
--space-8: 2rem; /* 32px */
|
|
116
|
-
--space-10: 2.5rem; /* 40px */
|
|
117
|
-
--space-12: 3rem; /* 48px */
|
|
118
|
-
--space-16: 4rem; /* 64px */
|
|
119
|
-
--space-20: 5rem; /* 80px */
|
|
120
|
-
--space-24: 6rem; /* 96px */
|
|
121
|
-
|
|
122
|
-
/* ========================================
|
|
123
|
-
* BORDER RADIUS
|
|
124
|
-
* ======================================== */
|
|
125
|
-
|
|
126
|
-
--rounded-none: 0;
|
|
127
|
-
--rounded-sm: 0.125rem; /* 2px */
|
|
128
|
-
--rounded-md: 0.375rem; /* 6px */
|
|
129
|
-
--rounded-lg: 0.5rem; /* 8px */
|
|
130
|
-
--rounded-xl: 0.75rem; /* 12px */
|
|
131
|
-
--rounded-2xl: 1rem; /* 16px */
|
|
132
|
-
--rounded-full: 9999px;
|
|
133
|
-
|
|
134
|
-
/* ========================================
|
|
135
|
-
* SOMBRAS (Shadows)
|
|
136
|
-
* ======================================== */
|
|
137
|
-
|
|
138
|
-
--shadow-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05);
|
|
139
|
-
--shadow-md: 0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06);
|
|
140
|
-
--shadow-lg: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05);
|
|
141
|
-
--shadow-xl: 0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04);
|
|
142
|
-
--shadow-2xl: 0 25px 50px -12px rgba(0, 0, 0, 0.25);
|
|
143
|
-
|
|
144
|
-
/* ========================================
|
|
145
|
-
* Z-INDEX LAYERS
|
|
146
|
-
* ======================================== */
|
|
147
|
-
|
|
148
|
-
--z-0: 0;
|
|
149
|
-
--z-10: 10;
|
|
150
|
-
--z-20: 20;
|
|
151
|
-
--z-30: 30;
|
|
152
|
-
--z-40: 40;
|
|
153
|
-
--z-50: 50; /* Modals, dropdowns */
|
|
154
|
-
--z-100: 100; /* Tooltips */
|
|
155
|
-
--z-max: 9999; /* Toasts, notifications */
|
|
156
|
-
|
|
157
|
-
/* ========================================
|
|
158
|
-
* TRANSITIONS / ANIMATIONS
|
|
159
|
-
* ======================================== */
|
|
160
|
-
|
|
161
|
-
--transition-fast: 150ms ease-in-out;
|
|
162
|
-
--transition-base: 250ms ease-in-out;
|
|
163
|
-
--transition-slow: 350ms ease-in-out;
|
|
164
|
-
|
|
165
|
-
--ease-in: cubic-bezier(0.4, 0, 1, 1);
|
|
166
|
-
--ease-out: cubic-bezier(0, 0, 0.2, 1);
|
|
167
|
-
--ease-in-out: cubic-bezier(0.4, 0, 0.2, 1);
|
|
168
|
-
|
|
169
|
-
/* ========================================
|
|
170
|
-
* BREAKPOINTS (informativo - usar em media queries)
|
|
171
|
-
* ======================================== */
|
|
172
|
-
|
|
173
|
-
/* @media (min-width: 640px) - sm */
|
|
174
|
-
/* @media (min-width: 768px) - md */
|
|
175
|
-
/* @media (min-width: 1024px) - lg */
|
|
176
|
-
/* @media (min-width: 1280px) - xl */
|
|
177
|
-
/* @media (min-width: 1536px) - 2xl */
|
|
178
|
-
}
|
|
179
|
-
|
|
180
|
-
/* ========================================
|
|
181
|
-
* MODO ESCURO (Dark Mode)
|
|
182
|
-
* Opcional - ajuste as cores para dark theme
|
|
183
|
-
* ======================================== */
|
|
184
|
-
|
|
185
|
-
@media (prefers-color-scheme: dark) {
|
|
186
|
-
:root {
|
|
187
|
-
/* Inverter cores conforme necessário */
|
|
188
|
-
--color-gray-50: #{hex do gray-900};
|
|
189
|
-
--color-gray-900: #{hex do gray-50};
|
|
190
|
-
/* ... outras inversões */
|
|
191
|
-
}
|
|
192
|
-
}
|
|
193
|
-
|
|
194
|
-
/* ========================================
|
|
195
|
-
* CLASSES UTILITÁRIAS (Exemplo)
|
|
196
|
-
* ======================================== */
|
|
197
|
-
|
|
198
|
-
/* Exemplo de uso das variáveis */
|
|
199
|
-
.btn-primary {
|
|
200
|
-
background-color: var(--color-primary);
|
|
201
|
-
color: white;
|
|
202
|
-
padding: var(--space-2) var(--space-4);
|
|
203
|
-
border-radius: var(--rounded-md);
|
|
204
|
-
font-weight: var(--font-semibold);
|
|
205
|
-
transition: background-color var(--transition-base);
|
|
206
|
-
}
|
|
207
|
-
|
|
208
|
-
.btn-primary:hover {
|
|
209
|
-
background-color: var(--color-primary-hover);
|
|
210
|
-
}
|
|
211
|
-
|
|
212
|
-
.card {
|
|
213
|
-
background-color: white;
|
|
214
|
-
padding: var(--space-6);
|
|
215
|
-
border-radius: var(--rounded-lg);
|
|
216
|
-
box-shadow: var(--shadow-md);
|
|
217
|
-
}
|
|
218
|
-
|
|
219
|
-
.text-muted {
|
|
220
|
-
color: var(--color-gray-600);
|
|
221
|
-
font-size: var(--text-sm);
|
|
222
|
-
}
|
|
223
|
-
|
|
224
|
-
/* ========================================
|
|
225
|
-
* FIM DO DESIGN SYSTEM
|
|
226
|
-
* ======================================== */
|
|
1
|
+
/**
|
|
2
|
+
* Design System - {Project Name}
|
|
3
|
+
*
|
|
4
|
+
* CSS Variables generated from design-system.md
|
|
5
|
+
* Use estas variáveis em todo o projeto para manter consistência visual.
|
|
6
|
+
*
|
|
7
|
+
* Template MORPH-SPEC by Polymorphism Tech
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
:root {
|
|
11
|
+
/* ========================================
|
|
12
|
+
* CORES PRINCIPAIS
|
|
13
|
+
* ======================================== */
|
|
14
|
+
|
|
15
|
+
--color-primary: #{hex da cor primária};
|
|
16
|
+
--color-primary-hover: #{hex da cor primária mais escura};
|
|
17
|
+
--color-primary-active: #{hex da cor primária ainda mais escura};
|
|
18
|
+
|
|
19
|
+
--color-secondary: #{hex da cor secundária};
|
|
20
|
+
--color-secondary-hover: #{hex};
|
|
21
|
+
--color-secondary-active: #{hex};
|
|
22
|
+
|
|
23
|
+
/* ========================================
|
|
24
|
+
* CORES DE ESTADO
|
|
25
|
+
* ======================================== */
|
|
26
|
+
|
|
27
|
+
--color-success: #{hex};
|
|
28
|
+
--color-success-bg: #{hex com transparência ou shade mais claro};
|
|
29
|
+
--color-success-border: #{hex};
|
|
30
|
+
|
|
31
|
+
--color-error: #{hex};
|
|
32
|
+
--color-error-bg: #{hex};
|
|
33
|
+
--color-error-border: #{hex};
|
|
34
|
+
|
|
35
|
+
--color-warning: #{hex};
|
|
36
|
+
--color-warning-bg: #{hex};
|
|
37
|
+
--color-warning-border: #{hex};
|
|
38
|
+
|
|
39
|
+
--color-info: #{hex};
|
|
40
|
+
--color-info-bg: #{hex};
|
|
41
|
+
--color-info-border: #{hex};
|
|
42
|
+
|
|
43
|
+
/* ========================================
|
|
44
|
+
* ESCALA DE NEUTROS (Cinzas)
|
|
45
|
+
* ======================================== */
|
|
46
|
+
|
|
47
|
+
--color-gray-50: #{hex};
|
|
48
|
+
--color-gray-100: #{hex};
|
|
49
|
+
--color-gray-200: #{hex};
|
|
50
|
+
--color-gray-300: #{hex};
|
|
51
|
+
--color-gray-400: #{hex};
|
|
52
|
+
--color-gray-500: #{hex};
|
|
53
|
+
--color-gray-600: #{hex};
|
|
54
|
+
--color-gray-700: #{hex};
|
|
55
|
+
--color-gray-800: #{hex};
|
|
56
|
+
--color-gray-900: #{hex};
|
|
57
|
+
|
|
58
|
+
/* ========================================
|
|
59
|
+
* TIPOGRAFIA - FONTES
|
|
60
|
+
* ======================================== */
|
|
61
|
+
|
|
62
|
+
--font-sans: '{Font Name}', -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', sans-serif;
|
|
63
|
+
--font-serif: '{Font Name}', Georgia, 'Times New Roman', serif;
|
|
64
|
+
--font-mono: '{Font Name}', 'Fira Code', 'Courier New', Consolas, monospace;
|
|
65
|
+
|
|
66
|
+
/* ========================================
|
|
67
|
+
* TIPOGRAFIA - TAMANHOS
|
|
68
|
+
* ======================================== */
|
|
69
|
+
|
|
70
|
+
--text-xs: 0.75rem; /* 12px */
|
|
71
|
+
--text-sm: 0.875rem; /* 14px */
|
|
72
|
+
--text-base: 1rem; /* 16px */
|
|
73
|
+
--text-lg: 1.125rem; /* 18px */
|
|
74
|
+
--text-xl: 1.25rem; /* 20px */
|
|
75
|
+
--text-2xl: 1.5rem; /* 24px */
|
|
76
|
+
--text-3xl: 1.875rem; /* 30px */
|
|
77
|
+
--text-4xl: 2.25rem; /* 36px */
|
|
78
|
+
--text-5xl: 3rem; /* 48px */
|
|
79
|
+
|
|
80
|
+
/* ========================================
|
|
81
|
+
* TIPOGRAFIA - LINE HEIGHTS
|
|
82
|
+
* ======================================== */
|
|
83
|
+
|
|
84
|
+
--leading-none: 1;
|
|
85
|
+
--leading-tight: 1.25;
|
|
86
|
+
--leading-snug: 1.375;
|
|
87
|
+
--leading-normal: 1.5;
|
|
88
|
+
--leading-relaxed: 1.625;
|
|
89
|
+
--leading-loose: 2;
|
|
90
|
+
|
|
91
|
+
/* ========================================
|
|
92
|
+
* TIPOGRAFIA - FONT WEIGHTS
|
|
93
|
+
* ======================================== */
|
|
94
|
+
|
|
95
|
+
--font-light: 300;
|
|
96
|
+
--font-regular: 400;
|
|
97
|
+
--font-medium: 500;
|
|
98
|
+
--font-semibold: 600;
|
|
99
|
+
--font-bold: 700;
|
|
100
|
+
--font-extrabold: 800;
|
|
101
|
+
|
|
102
|
+
/* ========================================
|
|
103
|
+
* ESPAÇAMENTO
|
|
104
|
+
* Baseado em múltiplos de {base}px (ex: 4px)
|
|
105
|
+
* ======================================== */
|
|
106
|
+
|
|
107
|
+
--space-0: 0;
|
|
108
|
+
--space-1: 0.25rem; /* 4px */
|
|
109
|
+
--space-2: 0.5rem; /* 8px */
|
|
110
|
+
--space-3: 0.75rem; /* 12px */
|
|
111
|
+
--space-4: 1rem; /* 16px */
|
|
112
|
+
--space-5: 1.25rem; /* 20px */
|
|
113
|
+
--space-6: 1.5rem; /* 24px */
|
|
114
|
+
--space-7: 1.75rem; /* 28px */
|
|
115
|
+
--space-8: 2rem; /* 32px */
|
|
116
|
+
--space-10: 2.5rem; /* 40px */
|
|
117
|
+
--space-12: 3rem; /* 48px */
|
|
118
|
+
--space-16: 4rem; /* 64px */
|
|
119
|
+
--space-20: 5rem; /* 80px */
|
|
120
|
+
--space-24: 6rem; /* 96px */
|
|
121
|
+
|
|
122
|
+
/* ========================================
|
|
123
|
+
* BORDER RADIUS
|
|
124
|
+
* ======================================== */
|
|
125
|
+
|
|
126
|
+
--rounded-none: 0;
|
|
127
|
+
--rounded-sm: 0.125rem; /* 2px */
|
|
128
|
+
--rounded-md: 0.375rem; /* 6px */
|
|
129
|
+
--rounded-lg: 0.5rem; /* 8px */
|
|
130
|
+
--rounded-xl: 0.75rem; /* 12px */
|
|
131
|
+
--rounded-2xl: 1rem; /* 16px */
|
|
132
|
+
--rounded-full: 9999px;
|
|
133
|
+
|
|
134
|
+
/* ========================================
|
|
135
|
+
* SOMBRAS (Shadows)
|
|
136
|
+
* ======================================== */
|
|
137
|
+
|
|
138
|
+
--shadow-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05);
|
|
139
|
+
--shadow-md: 0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06);
|
|
140
|
+
--shadow-lg: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05);
|
|
141
|
+
--shadow-xl: 0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04);
|
|
142
|
+
--shadow-2xl: 0 25px 50px -12px rgba(0, 0, 0, 0.25);
|
|
143
|
+
|
|
144
|
+
/* ========================================
|
|
145
|
+
* Z-INDEX LAYERS
|
|
146
|
+
* ======================================== */
|
|
147
|
+
|
|
148
|
+
--z-0: 0;
|
|
149
|
+
--z-10: 10;
|
|
150
|
+
--z-20: 20;
|
|
151
|
+
--z-30: 30;
|
|
152
|
+
--z-40: 40;
|
|
153
|
+
--z-50: 50; /* Modals, dropdowns */
|
|
154
|
+
--z-100: 100; /* Tooltips */
|
|
155
|
+
--z-max: 9999; /* Toasts, notifications */
|
|
156
|
+
|
|
157
|
+
/* ========================================
|
|
158
|
+
* TRANSITIONS / ANIMATIONS
|
|
159
|
+
* ======================================== */
|
|
160
|
+
|
|
161
|
+
--transition-fast: 150ms ease-in-out;
|
|
162
|
+
--transition-base: 250ms ease-in-out;
|
|
163
|
+
--transition-slow: 350ms ease-in-out;
|
|
164
|
+
|
|
165
|
+
--ease-in: cubic-bezier(0.4, 0, 1, 1);
|
|
166
|
+
--ease-out: cubic-bezier(0, 0, 0.2, 1);
|
|
167
|
+
--ease-in-out: cubic-bezier(0.4, 0, 0.2, 1);
|
|
168
|
+
|
|
169
|
+
/* ========================================
|
|
170
|
+
* BREAKPOINTS (informativo - usar em media queries)
|
|
171
|
+
* ======================================== */
|
|
172
|
+
|
|
173
|
+
/* @media (min-width: 640px) - sm */
|
|
174
|
+
/* @media (min-width: 768px) - md */
|
|
175
|
+
/* @media (min-width: 1024px) - lg */
|
|
176
|
+
/* @media (min-width: 1280px) - xl */
|
|
177
|
+
/* @media (min-width: 1536px) - 2xl */
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
/* ========================================
|
|
181
|
+
* MODO ESCURO (Dark Mode)
|
|
182
|
+
* Opcional - ajuste as cores para dark theme
|
|
183
|
+
* ======================================== */
|
|
184
|
+
|
|
185
|
+
@media (prefers-color-scheme: dark) {
|
|
186
|
+
:root {
|
|
187
|
+
/* Inverter cores conforme necessário */
|
|
188
|
+
--color-gray-50: #{hex do gray-900};
|
|
189
|
+
--color-gray-900: #{hex do gray-50};
|
|
190
|
+
/* ... outras inversões */
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
/* ========================================
|
|
195
|
+
* CLASSES UTILITÁRIAS (Exemplo)
|
|
196
|
+
* ======================================== */
|
|
197
|
+
|
|
198
|
+
/* Exemplo de uso das variáveis */
|
|
199
|
+
.btn-primary {
|
|
200
|
+
background-color: var(--color-primary);
|
|
201
|
+
color: white;
|
|
202
|
+
padding: var(--space-2) var(--space-4);
|
|
203
|
+
border-radius: var(--rounded-md);
|
|
204
|
+
font-weight: var(--font-semibold);
|
|
205
|
+
transition: background-color var(--transition-base);
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
.btn-primary:hover {
|
|
209
|
+
background-color: var(--color-primary-hover);
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
.card {
|
|
213
|
+
background-color: white;
|
|
214
|
+
padding: var(--space-6);
|
|
215
|
+
border-radius: var(--rounded-lg);
|
|
216
|
+
box-shadow: var(--shadow-md);
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
.text-muted {
|
|
220
|
+
color: var(--color-gray-600);
|
|
221
|
+
font-size: var(--text-sm);
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
/* ========================================
|
|
225
|
+
* FIM DO DESIGN SYSTEM
|
|
226
|
+
* ======================================== */
|
package/package.json
CHANGED
package/src/commands/e2e/e2e.js
CHANGED
|
@@ -16,7 +16,9 @@ import {
|
|
|
16
16
|
deleteStamp,
|
|
17
17
|
getStackStatus,
|
|
18
18
|
isDockerAvailable,
|
|
19
|
+
isHostOnlyStack,
|
|
19
20
|
lintComposeIsolation,
|
|
21
|
+
resetE2eData,
|
|
20
22
|
readStamp,
|
|
21
23
|
resolveComposeFile,
|
|
22
24
|
resolveSpecCommand,
|
|
@@ -34,8 +36,9 @@ import { readHeavyConfig } from '../../../framework/hooks/shared/heavy-config.js
|
|
|
34
36
|
const EXIT_USAGE = 2;
|
|
35
37
|
const EXIT_BUSY = 3;
|
|
36
38
|
|
|
37
|
-
// No compose file is a usage error here, unlike in the verify node where
|
|
38
|
-
|
|
39
|
+
// No compose file and no e2e.hostServices is a usage error here, unlike in the verify node where
|
|
40
|
+
// it is a graded skip. `composeFile` is null for a host-only stack.
|
|
41
|
+
function resolveContext(featureName, { json = false, onMissing } = {}) {
|
|
39
42
|
const root = resolvePrimaryRoot(process.cwd());
|
|
40
43
|
const found = findWorktreeForFeature(featureName, root);
|
|
41
44
|
const cwd = found?.path ?? root;
|
|
@@ -43,11 +46,13 @@ function resolveContext(featureName, { json = false } = {}) {
|
|
|
43
46
|
const config = readConfig(cwd) ?? readConfig(root);
|
|
44
47
|
const composeFile = resolveComposeFile(cwd, config);
|
|
45
48
|
|
|
46
|
-
if (!composeFile) {
|
|
49
|
+
if (!composeFile && !isHostOnlyStack(config, composeFile)) {
|
|
47
50
|
const message =
|
|
48
|
-
`No compose file found in ${cwd} (compose.yaml, docker-compose.yml, …). ` +
|
|
49
|
-
'Set
|
|
50
|
-
|
|
51
|
+
`No compose file found in ${cwd} (compose.yaml, docker-compose.yml, …) and no e2e.hostServices. ` +
|
|
52
|
+
'Set e2e.composeFile in .morph/config/config.json if it lives elsewhere, ' +
|
|
53
|
+
'or declare the app in e2e.hostServices when it has no dependency to containerize.';
|
|
54
|
+
if (onMissing) onMissing(message, cwd);
|
|
55
|
+
else if (json) console.log(JSON.stringify({ error: message, tree: cwd }, null, 2));
|
|
51
56
|
else console.error(chalk.red(`\n❌ ${message}\n`));
|
|
52
57
|
return null;
|
|
53
58
|
}
|
|
@@ -86,7 +91,7 @@ export async function e2eUpCommand(featureName, options = {}) {
|
|
|
86
91
|
|
|
87
92
|
// Isolation BEFORE the docker check: a compose that hardcodes host ports or container names
|
|
88
93
|
// collides with a sibling worktree whatever we inject.
|
|
89
|
-
const lint = lintComposeIsolation(readComposeText(ctx.cwd, ctx.composeFile));
|
|
94
|
+
const lint = ctx.composeFile ? lintComposeIsolation(readComposeText(ctx.cwd, ctx.composeFile)) : { findings: [] };
|
|
90
95
|
const isolation = decideIsolation({ findings: lint.findings, insideWorktree: ctx.insideWorktree });
|
|
91
96
|
if (isolation.status === 'fail') {
|
|
92
97
|
if (options.json) {
|
|
@@ -106,7 +111,7 @@ export async function e2eUpCommand(featureName, options = {}) {
|
|
|
106
111
|
}
|
|
107
112
|
|
|
108
113
|
const exec = options._exec ?? defaultExec;
|
|
109
|
-
if (!isDockerAvailable(ctx.cwd, exec)) {
|
|
114
|
+
if (ctx.composeFile && !isDockerAvailable(ctx.cwd, exec)) {
|
|
110
115
|
console.error(chalk.red('\n❌ Docker is not available in this environment.\n'));
|
|
111
116
|
process.exit(EXIT_USAGE);
|
|
112
117
|
}
|
|
@@ -149,7 +154,7 @@ export async function e2eUpCommand(featureName, options = {}) {
|
|
|
149
154
|
tree: ctx.tree,
|
|
150
155
|
composeFile: ctx.composeFile,
|
|
151
156
|
status: failed ? 'fail' : 'pass',
|
|
152
|
-
reused: result.stack.reused,
|
|
157
|
+
reused: ctx.composeFile ? result.stack.reused : hostServices.reused,
|
|
153
158
|
reason: result.reason,
|
|
154
159
|
auth: { status: auth.status, reason: auth.reason },
|
|
155
160
|
...(hostServices.status === 'skip' ? {} : { hostServices: hostServices.services }),
|
|
@@ -164,7 +169,9 @@ export async function e2eUpCommand(featureName, options = {}) {
|
|
|
164
169
|
if (result.output) console.error(result.output);
|
|
165
170
|
for (const w of result.warnings) console.error(chalk.yellow(`⚠️ ${w}`));
|
|
166
171
|
} else {
|
|
167
|
-
const how =
|
|
172
|
+
const how = !ctx.composeFile
|
|
173
|
+
? chalk.gray(`(${result.stack.reason})`)
|
|
174
|
+
: result.stack.reused ? chalk.gray(`(${result.stack.reason})`) : chalk.gray('(built)');
|
|
168
175
|
console.log(chalk.green(`\n✓ Stack up — ${ctx.projectName} ${how}`));
|
|
169
176
|
console.log(chalk.gray(` tree: ${ctx.tree}`));
|
|
170
177
|
for (const s of hostServices.services) {
|
|
@@ -190,18 +197,24 @@ export async function e2eStatusCommand(featureName, options = {}) {
|
|
|
190
197
|
if (!ctx) process.exit(EXIT_USAGE);
|
|
191
198
|
|
|
192
199
|
const exec = options._exec ?? defaultExec;
|
|
193
|
-
const
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
200
|
+
const hostServices = ctx.gitCommonDir ? hostServicesStatus(ctx.gitCommonDir, ctx.projectName) : [];
|
|
201
|
+
const status = ctx.composeFile
|
|
202
|
+
? getStackStatus(ctx.cwd, {
|
|
203
|
+
composeFile: ctx.composeFile,
|
|
204
|
+
projectName: ctx.projectName,
|
|
205
|
+
env: ctx.env,
|
|
206
|
+
}, exec)
|
|
207
|
+
: {
|
|
208
|
+
up: hostServices.length > 0 && hostServices.every((h) => h.alive),
|
|
209
|
+
healthy: hostServices.length > 0 && hostServices.every((h) => h.alive && h.health !== false),
|
|
210
|
+
services: [],
|
|
211
|
+
};
|
|
198
212
|
|
|
199
213
|
const stamp = computeSourceStamp(ctx.cwd, exec);
|
|
200
214
|
const previous = ctx.gitCommonDir ? readStamp(ctx.gitCommonDir, ctx.projectName) : null;
|
|
201
215
|
const fresh = Boolean(stamp && previous?.stamp === stamp);
|
|
202
216
|
|
|
203
217
|
const spec = resolveSpecCommand(ctx.cwd, ctx.config, ctx.config?.project?.frontendPath);
|
|
204
|
-
const hostServices = ctx.gitCommonDir ? hostServicesStatus(ctx.gitCommonDir, ctx.projectName) : [];
|
|
205
218
|
|
|
206
219
|
const payload = {
|
|
207
220
|
feature: featureName,
|
|
@@ -228,7 +241,7 @@ export async function e2eStatusCommand(featureName, options = {}) {
|
|
|
228
241
|
console.log('');
|
|
229
242
|
console.log(chalk.bold(`E2E stack — ${ctx.projectName}`));
|
|
230
243
|
console.log(chalk.gray(`tree: ${ctx.tree}`));
|
|
231
|
-
console.log(chalk.gray(`compose: ${ctx.composeFile}`));
|
|
244
|
+
console.log(chalk.gray(`compose: ${ctx.composeFile ?? 'none (host services only)'}`));
|
|
232
245
|
console.log(chalk.gray(`url: ${payload.baseUrl}`));
|
|
233
246
|
console.log('');
|
|
234
247
|
console.log(` up ${status.up ? chalk.green('yes') : chalk.gray('no')}`);
|
|
@@ -257,12 +270,14 @@ export async function e2eDownCommand(featureName, options = {}) {
|
|
|
257
270
|
if (!ctx) process.exit(EXIT_USAGE);
|
|
258
271
|
|
|
259
272
|
const hostServices = stopHostServices(ctx.gitCommonDir, ctx.projectName);
|
|
260
|
-
const result =
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
273
|
+
const result = ctx.composeFile
|
|
274
|
+
? tearDownStack(ctx.cwd, {
|
|
275
|
+
composeFile: ctx.composeFile,
|
|
276
|
+
projectName: ctx.projectName,
|
|
277
|
+
env: ctx.env,
|
|
278
|
+
volumes: Boolean(options.volumes),
|
|
279
|
+
}, options._exec ?? defaultExec)
|
|
280
|
+
: { status: 'pass', output: '' };
|
|
266
281
|
const stampDeleted = deleteStamp(ctx.gitCommonDir, ctx.projectName);
|
|
267
282
|
const cleanup = afterHeavyRun({ projectPath: ctx.cwd, config: readHeavyConfig(ctx.cwd) });
|
|
268
283
|
|
|
@@ -288,6 +303,56 @@ export async function e2eDownCommand(featureName, options = {}) {
|
|
|
288
303
|
process.exit(0);
|
|
289
304
|
}
|
|
290
305
|
|
|
306
|
+
// Between the verifier's flows: the next flow starts from the seeded state, not from the rows the
|
|
307
|
+
// previous one left. Exit 1 only on fail; skip (nothing configured to reset) is exit 0.
|
|
308
|
+
export async function e2eResetCommand(featureName, options = {}) {
|
|
309
|
+
const emit = (payload) => {
|
|
310
|
+
if (options.json) {
|
|
311
|
+
console.log(JSON.stringify(payload, null, 2));
|
|
312
|
+
} else if (payload.status === 'fail') {
|
|
313
|
+
console.error(chalk.red(`\n✗ ${payload.reason}\n`));
|
|
314
|
+
if (payload.output) console.error(payload.output);
|
|
315
|
+
} else if (payload.status === 'skip') {
|
|
316
|
+
console.log(chalk.gray(`\n○ e2e reset: ${payload.reason}\n`));
|
|
317
|
+
} else {
|
|
318
|
+
const what = payload.reset.mode === 'command'
|
|
319
|
+
? `e2e.resetCommand (${payload.reset.command})`
|
|
320
|
+
: payload.reset.mode === 'volumes'
|
|
321
|
+
? `recreated ${payload.reset.services.join(', ')} (volumes ${payload.reset.volumes.join(', ')})`
|
|
322
|
+
: 'no data reset';
|
|
323
|
+
console.log(chalk.green(`\n✓ e2e reset — ${what}`));
|
|
324
|
+
if (payload.auth.reason) console.log(chalk.gray(` auth: ${payload.auth.reason}`));
|
|
325
|
+
console.log('');
|
|
326
|
+
}
|
|
327
|
+
process.exit(payload.status === 'fail' ? 1 : 0);
|
|
328
|
+
};
|
|
329
|
+
|
|
330
|
+
const ctx = resolveContext(featureName, {
|
|
331
|
+
...options,
|
|
332
|
+
onMissing: (message, tree) => emit({ feature: featureName, tree, status: 'fail', reason: message }),
|
|
333
|
+
});
|
|
334
|
+
if (!ctx) return;
|
|
335
|
+
|
|
336
|
+
const result = resetE2eData(ctx.cwd, {
|
|
337
|
+
config: ctx.config,
|
|
338
|
+
composeFile: ctx.composeFile,
|
|
339
|
+
projectName: ctx.projectName,
|
|
340
|
+
gitCommonDir: ctx.gitCommonDir,
|
|
341
|
+
env: ctx.env,
|
|
342
|
+
}, options._exec ?? defaultExec);
|
|
343
|
+
|
|
344
|
+
emit({
|
|
345
|
+
feature: featureName,
|
|
346
|
+
project: ctx.projectName,
|
|
347
|
+
tree: ctx.tree,
|
|
348
|
+
status: result.status,
|
|
349
|
+
reason: result.reason,
|
|
350
|
+
reset: result.reset,
|
|
351
|
+
auth: result.auth,
|
|
352
|
+
...(result.status === 'fail' && result.output ? { output: result.output } : {}),
|
|
353
|
+
});
|
|
354
|
+
}
|
|
355
|
+
|
|
291
356
|
function stoppedAnything({ killed, skipped, warnings }) {
|
|
292
357
|
return killed.length + skipped.length + warnings.length > 0;
|
|
293
358
|
}
|