@hivehub/rulebook 5.1.2 → 5.1.3
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/commands/continue.md +33 -33
- package/.claude/commands/ralph-config.md +112 -112
- package/.claude/commands/ralph-history.md +110 -110
- package/.claude/commands/ralph-init.md +72 -72
- package/.claude/commands/ralph-pause-resume.md +105 -105
- package/.claude/commands/ralph-run.md +101 -101
- package/.claude/commands/ralph-status.md +76 -76
- package/.claude/commands/rulebook-decision-create.md +55 -55
- package/.claude/commands/rulebook-decision-list.md +15 -15
- package/.claude/commands/rulebook-knowledge-add.md +41 -41
- package/.claude/commands/rulebook-knowledge-list.md +15 -15
- package/.claude/commands/rulebook-learn-capture.md +48 -48
- package/.claude/commands/rulebook-learn-list.md +13 -13
- package/.claude/commands/rulebook-memory-save.md +48 -48
- package/.claude/commands/rulebook-memory-search.md +47 -47
- package/.claude/commands/rulebook-task-apply.md +67 -67
- package/.claude/commands/rulebook-task-archive.md +94 -94
- package/.claude/commands/rulebook-task-create.md +93 -93
- package/.claude/commands/rulebook-task-list.md +42 -42
- package/.claude/commands/rulebook-task-show.md +52 -52
- package/.claude/commands/rulebook-task-validate.md +53 -53
- package/.claude-plugin/marketplace.json +28 -28
- package/.claude-plugin/plugin.json +8 -8
- package/README.md +4 -0
- package/dist/cli/commands.d.ts.map +1 -1
- package/dist/cli/commands.js +39 -8
- package/dist/cli/commands.js.map +1 -1
- package/dist/core/agent-template-engine.d.ts.map +1 -1
- package/dist/core/agent-template-engine.js +36 -30
- package/dist/core/agent-template-engine.js.map +1 -1
- package/dist/core/complexity-detector.d.ts.map +1 -1
- package/dist/core/complexity-detector.js +109 -29
- package/dist/core/complexity-detector.js.map +1 -1
- package/dist/core/decision-manager.d.ts.map +1 -1
- package/dist/core/decision-manager.js +2 -7
- package/dist/core/decision-manager.js.map +1 -1
- package/dist/core/generator.d.ts.map +1 -1
- package/dist/core/generator.js +28 -28
- package/dist/core/generator.js.map +1 -1
- package/dist/core/indexer/background-indexer.d.ts +1 -0
- package/dist/core/indexer/background-indexer.d.ts.map +1 -1
- package/dist/core/indexer/background-indexer.js +107 -19
- package/dist/core/indexer/background-indexer.js.map +1 -1
- package/dist/core/indexer/indexer-types.d.ts +2 -0
- package/dist/core/indexer/indexer-types.d.ts.map +1 -1
- package/dist/core/knowledge-manager.d.ts.map +1 -1
- package/dist/core/knowledge-manager.js +1 -1
- package/dist/core/knowledge-manager.js.map +1 -1
- package/dist/core/learn-manager.d.ts.map +1 -1
- package/dist/core/learn-manager.js +1 -1
- package/dist/core/learn-manager.js.map +1 -1
- package/dist/core/rule-engine.d.ts.map +1 -1
- package/dist/core/rule-engine.js +1 -3
- package/dist/core/rule-engine.js.map +1 -1
- package/dist/core/task-manager.d.ts.map +1 -1
- package/dist/core/task-manager.js +24 -24
- package/dist/core/task-manager.js.map +1 -1
- package/dist/index.js +23 -7
- package/dist/index.js.map +1 -1
- package/dist/mcp/rulebook-server.d.ts.map +1 -1
- package/dist/mcp/rulebook-server.js +18 -6
- package/dist/mcp/rulebook-server.js.map +1 -1
- package/dist/memory/hnsw-index.d.ts.map +1 -1
- package/dist/memory/hnsw-index.js +12 -4
- package/dist/memory/hnsw-index.js.map +1 -1
- package/dist/memory/memory-store.d.ts.map +1 -1
- package/dist/memory/memory-store.js +136 -107
- package/dist/memory/memory-store.js.map +1 -1
- package/dist/types.d.ts +7 -0
- package/dist/types.d.ts.map +1 -1
- package/package.json +22 -21
- package/templates/agents/accessibility-reviewer.md +43 -43
- package/templates/agents/api-designer.md +42 -42
- package/templates/agents/architect.md +51 -51
- package/templates/agents/build-engineer.md +36 -36
- package/templates/agents/code-reviewer.md +47 -47
- package/templates/agents/compiler/codegen-debugger.md +34 -34
- package/templates/agents/compiler/stdlib-engineer.md +28 -28
- package/templates/agents/compiler/test-coverage-guardian.md +31 -31
- package/templates/agents/context-intelligence.md +52 -52
- package/templates/agents/database-architect.md +41 -41
- package/templates/agents/devops-engineer.md +42 -42
- package/templates/agents/docs-writer.md +38 -38
- package/templates/agents/game-engine/cpp-core-expert.md +35 -35
- package/templates/agents/game-engine/render-engineer.md +22 -22
- package/templates/agents/game-engine/shader-engineer.md +38 -38
- package/templates/agents/game-engine/systems-integration.md +43 -43
- package/templates/agents/generic/code-reviewer.md +41 -41
- package/templates/agents/generic/docs-writer.md +25 -25
- package/templates/agents/generic/project-manager.md +36 -36
- package/templates/agents/generic/researcher.md +34 -34
- package/templates/agents/generic/test-engineer.md +41 -41
- package/templates/agents/i18n-engineer.md +42 -42
- package/templates/agents/implementer.md +42 -42
- package/templates/agents/migration-engineer.md +42 -42
- package/templates/agents/mobile/platform-specialist.md +22 -22
- package/templates/agents/mobile/ui-engineer.md +22 -22
- package/templates/agents/performance-engineer.md +49 -49
- package/templates/agents/refactoring-agent.md +41 -41
- package/templates/agents/researcher.md +38 -38
- package/templates/agents/security-reviewer.md +40 -40
- package/templates/agents/team-lead.md +37 -37
- package/templates/agents/tester.md +48 -48
- package/templates/agents/ux-reviewer.md +43 -43
- package/templates/agents/web-app/api-designer.md +22 -22
- package/templates/agents/web-app/backend-engineer.md +30 -30
- package/templates/agents/web-app/database-engineer.md +22 -22
- package/templates/agents/web-app/frontend-engineer.md +29 -29
- package/templates/agents/web-app/security-reviewer.md +32 -32
- package/templates/ci/rulebook-review.yml +26 -26
- package/templates/cli/AIDER.md +49 -49
- package/templates/cli/AMAZON_Q.md +25 -25
- package/templates/cli/AUGGIE.md +32 -32
- package/templates/cli/CLAUDE.md +117 -117
- package/templates/cli/CLINE.md +99 -99
- package/templates/cli/CODEBUDDY.md +20 -20
- package/templates/cli/CODEIUM.md +20 -20
- package/templates/cli/CODEX.md +21 -21
- package/templates/cli/CONTINUE.md +34 -34
- package/templates/cli/CURSOR_CLI.md +62 -62
- package/templates/cli/FACTORY.md +18 -18
- package/templates/cli/GEMINI.md +35 -35
- package/templates/cli/KILOCODE.md +18 -18
- package/templates/cli/OPENCODE.md +18 -18
- package/templates/cli/_GENERIC_TEMPLATE.md +29 -29
- package/templates/commands/rulebook-decision-create.md +55 -55
- package/templates/commands/rulebook-decision-list.md +15 -15
- package/templates/commands/rulebook-knowledge-add.md +41 -41
- package/templates/commands/rulebook-knowledge-list.md +15 -15
- package/templates/commands/rulebook-learn-capture.md +48 -48
- package/templates/commands/rulebook-learn-list.md +13 -13
- package/templates/commands/rulebook-memory-save.md +48 -48
- package/templates/commands/rulebook-memory-search.md +47 -47
- package/templates/commands/rulebook-task-apply.md +67 -67
- package/templates/commands/rulebook-task-archive.md +94 -94
- package/templates/commands/rulebook-task-create.md +93 -93
- package/templates/commands/rulebook-task-list.md +42 -42
- package/templates/commands/rulebook-task-show.md +52 -52
- package/templates/commands/rulebook-task-validate.md +53 -53
- package/templates/core/AGENTS_LEAN.md +25 -25
- package/templates/core/AGENTS_OVERRIDE.md +16 -16
- package/templates/core/AGENT_AUTOMATION.md +296 -296
- package/templates/core/DAG.md +304 -304
- package/templates/core/DECISIONS.md +38 -38
- package/templates/core/DOCUMENTATION_RULES.md +36 -36
- package/templates/core/KNOWLEDGE.md +49 -49
- package/templates/core/MULTI_AGENT.md +74 -74
- package/templates/core/PLANS.md +28 -28
- package/templates/core/QUALITY_ENFORCEMENT.md +68 -68
- package/templates/core/RALPH.md +471 -471
- package/templates/core/RULEBOOK.md +1947 -1947
- package/templates/core/TIER1_PROHIBITIONS.md +154 -154
- package/templates/core/TOKEN_OPTIMIZATION.md +49 -49
- package/templates/frameworks/ANGULAR.md +36 -36
- package/templates/frameworks/DJANGO.md +83 -83
- package/templates/frameworks/ELECTRON.md +147 -147
- package/templates/frameworks/FLASK.md +38 -38
- package/templates/frameworks/FLUTTER.md +55 -55
- package/templates/frameworks/JQUERY.md +32 -32
- package/templates/frameworks/LARAVEL.md +38 -38
- package/templates/frameworks/NESTJS.md +43 -43
- package/templates/frameworks/NEXTJS.md +127 -127
- package/templates/frameworks/NUXT.md +40 -40
- package/templates/frameworks/RAILS.md +66 -66
- package/templates/frameworks/REACT.md +38 -38
- package/templates/frameworks/REACT_NATIVE.md +47 -47
- package/templates/frameworks/SPRING.md +39 -39
- package/templates/frameworks/SYMFONY.md +36 -36
- package/templates/frameworks/VUE.md +36 -36
- package/templates/frameworks/ZEND.md +35 -35
- package/templates/git/CI_CD_PATTERNS.md +661 -661
- package/templates/git/GITHUB_ACTIONS.md +728 -728
- package/templates/git/GITLAB_CI.md +730 -730
- package/templates/git/GIT_WORKFLOW.md +1192 -1192
- package/templates/git/SECRETS_MANAGEMENT.md +585 -585
- package/templates/hooks/COMMIT_MSG.md +530 -530
- package/templates/hooks/POST_CHECKOUT.md +546 -546
- package/templates/hooks/PREPARE_COMMIT_MSG.md +619 -619
- package/templates/hooks/PRE_COMMIT.md +414 -414
- package/templates/hooks/PRE_PUSH.md +601 -601
- package/templates/ides/CONTINUE_RULES.md +16 -16
- package/templates/ides/COPILOT.md +37 -37
- package/templates/ides/COPILOT_INSTRUCTIONS.md +23 -23
- package/templates/ides/CURSOR.md +43 -43
- package/templates/ides/GEMINI_RULES.md +17 -17
- package/templates/ides/JETBRAINS_AI.md +35 -35
- package/templates/ides/REPLIT.md +36 -36
- package/templates/ides/TABNINE.md +29 -29
- package/templates/ides/VSCODE.md +40 -40
- package/templates/ides/WINDSURF.md +36 -36
- package/templates/ides/WINDSURF_RULES.md +14 -14
- package/templates/ides/ZED.md +32 -32
- package/templates/ides/cursor-mdc/go.mdc +24 -24
- package/templates/ides/cursor-mdc/python.mdc +24 -24
- package/templates/ides/cursor-mdc/quality.mdc +25 -25
- package/templates/ides/cursor-mdc/ralph.mdc +39 -39
- package/templates/ides/cursor-mdc/rulebook.mdc +38 -38
- package/templates/ides/cursor-mdc/rust.mdc +24 -24
- package/templates/ides/cursor-mdc/typescript.mdc +25 -25
- package/templates/languages/C.md +333 -333
- package/templates/languages/CPP.md +743 -743
- package/templates/languages/CSHARP.md +417 -417
- package/templates/languages/ELIXIR.md +454 -454
- package/templates/languages/ERLANG.md +361 -361
- package/templates/languages/GO.md +645 -645
- package/templates/languages/HASKELL.md +177 -177
- package/templates/languages/JAVA.md +607 -607
- package/templates/languages/JAVASCRIPT.md +631 -631
- package/templates/languages/JULIA.md +97 -97
- package/templates/languages/KOTLIN.md +511 -511
- package/templates/languages/LISP.md +100 -100
- package/templates/languages/LUA.md +74 -74
- package/templates/languages/OBJECTIVEC.md +90 -90
- package/templates/languages/PHP.md +416 -416
- package/templates/languages/PYTHON.md +682 -682
- package/templates/languages/RUBY.md +421 -421
- package/templates/languages/RUST.md +477 -477
- package/templates/languages/SAS.md +73 -73
- package/templates/languages/SCALA.md +348 -348
- package/templates/languages/SOLIDITY.md +580 -580
- package/templates/languages/SQL.md +137 -137
- package/templates/languages/SWIFT.md +466 -466
- package/templates/languages/TYPESCRIPT.md +591 -591
- package/templates/languages/ZIG.md +265 -265
- package/templates/modules/ATLASSIAN.md +255 -255
- package/templates/modules/CONTEXT7.md +54 -54
- package/templates/modules/FIGMA.md +267 -267
- package/templates/modules/GITHUB_MCP.md +64 -64
- package/templates/modules/GRAFANA.md +328 -328
- package/templates/modules/MEMORY.md +126 -126
- package/templates/modules/NOTION.md +247 -247
- package/templates/modules/PLAYWRIGHT.md +90 -90
- package/templates/modules/RULEBOOK_MCP.md +156 -156
- package/templates/modules/SERENA.md +337 -337
- package/templates/modules/SUPABASE.md +223 -223
- package/templates/modules/SYNAP.md +69 -69
- package/templates/modules/VECTORIZER.md +63 -63
- package/templates/modules/sequential-thinking.md +42 -42
- package/templates/ralph/ralph-history.bat +4 -4
- package/templates/ralph/ralph-history.sh +5 -5
- package/templates/ralph/ralph-init.bat +5 -5
- package/templates/ralph/ralph-init.sh +5 -5
- package/templates/ralph/ralph-pause.bat +5 -5
- package/templates/ralph/ralph-pause.sh +5 -5
- package/templates/ralph/ralph-run.bat +5 -5
- package/templates/ralph/ralph-run.sh +5 -5
- package/templates/ralph/ralph-status.bat +4 -4
- package/templates/ralph/ralph-status.sh +5 -5
- package/templates/rules/follow-task-sequence.md +36 -36
- package/templates/rules/git-safety.md +29 -29
- package/templates/rules/incremental-tests.md +29 -29
- package/templates/rules/no-deferred.md +31 -31
- package/templates/rules/no-shortcuts.md +30 -30
- package/templates/rules/research-first.md +30 -30
- package/templates/rules/sequential-editing.md +21 -21
- package/templates/rules/session-workflow.md +24 -24
- package/templates/rules/task-decomposition.md +32 -32
- package/templates/services/AZURE_BLOB.md +184 -184
- package/templates/services/CASSANDRA.md +239 -239
- package/templates/services/DATADOG.md +26 -26
- package/templates/services/DOCKER.md +124 -124
- package/templates/services/DOCKER_COMPOSE.md +168 -168
- package/templates/services/DYNAMODB.md +308 -308
- package/templates/services/ELASTICSEARCH.md +347 -347
- package/templates/services/GCS.md +178 -178
- package/templates/services/HELM.md +194 -194
- package/templates/services/INFLUXDB.md +265 -265
- package/templates/services/KAFKA.md +341 -341
- package/templates/services/KUBERNETES.md +208 -208
- package/templates/services/MARIADB.md +183 -183
- package/templates/services/MEMCACHED.md +242 -242
- package/templates/services/MINIO.md +201 -201
- package/templates/services/MONGODB.md +268 -268
- package/templates/services/MYSQL.md +358 -358
- package/templates/services/NEO4J.md +247 -247
- package/templates/services/OPENTELEMETRY.md +25 -25
- package/templates/services/ORACLE.md +290 -290
- package/templates/services/PINO.md +24 -24
- package/templates/services/POSTGRESQL.md +326 -326
- package/templates/services/PROMETHEUS.md +33 -33
- package/templates/services/RABBITMQ.md +286 -286
- package/templates/services/REDIS.md +292 -292
- package/templates/services/S3.md +298 -298
- package/templates/services/SENTRY.md +23 -23
- package/templates/services/SQLITE.md +294 -294
- package/templates/services/SQLSERVER.md +294 -294
- package/templates/services/WINSTON.md +30 -30
- package/templates/skills/cli/aider/SKILL.md +59 -59
- package/templates/skills/cli/amazon-q/SKILL.md +35 -35
- package/templates/skills/cli/auggie/SKILL.md +42 -42
- package/templates/skills/cli/claude/SKILL.md +42 -42
- package/templates/skills/cli/cline/SKILL.md +42 -42
- package/templates/skills/cli/codebuddy/SKILL.md +30 -30
- package/templates/skills/cli/codeium/SKILL.md +30 -30
- package/templates/skills/cli/codex/SKILL.md +31 -31
- package/templates/skills/cli/continue/SKILL.md +44 -44
- package/templates/skills/cli/cursor-cli/SKILL.md +38 -38
- package/templates/skills/cli/factory/SKILL.md +28 -28
- package/templates/skills/cli/gemini/SKILL.md +45 -45
- package/templates/skills/cli/kilocode/SKILL.md +28 -28
- package/templates/skills/cli/opencode/SKILL.md +28 -28
- package/templates/skills/core/agent-automation/SKILL.md +194 -194
- package/templates/skills/core/dag/SKILL.md +314 -314
- package/templates/skills/core/documentation-rules/SKILL.md +46 -46
- package/templates/skills/core/quality-enforcement/SKILL.md +78 -78
- package/templates/skills/core/rulebook/SKILL.md +176 -176
- package/templates/skills/dev/accessibility/SKILL.md +17 -17
- package/templates/skills/dev/api-design/SKILL.md +15 -15
- package/templates/skills/dev/architect/SKILL.md +17 -17
- package/templates/skills/dev/build-fix/SKILL.md +17 -17
- package/templates/skills/dev/db-design/SKILL.md +15 -15
- package/templates/skills/dev/debug/SKILL.md +16 -16
- package/templates/skills/dev/deploy/SKILL.md +17 -17
- package/templates/skills/dev/docs/SKILL.md +17 -17
- package/templates/skills/dev/migrate/SKILL.md +15 -15
- package/templates/skills/dev/perf/SKILL.md +17 -17
- package/templates/skills/dev/refactor/SKILL.md +17 -17
- package/templates/skills/dev/research/SKILL.md +14 -14
- package/templates/skills/dev/review/SKILL.md +18 -18
- package/templates/skills/dev/security-audit/SKILL.md +17 -17
- package/templates/skills/frameworks/angular/SKILL.md +46 -46
- package/templates/skills/frameworks/django/SKILL.md +93 -93
- package/templates/skills/frameworks/electron/SKILL.md +157 -157
- package/templates/skills/frameworks/flask/SKILL.md +48 -48
- package/templates/skills/frameworks/flutter/SKILL.md +65 -65
- package/templates/skills/frameworks/jquery/SKILL.md +42 -42
- package/templates/skills/frameworks/laravel/SKILL.md +48 -48
- package/templates/skills/frameworks/nestjs/SKILL.md +53 -53
- package/templates/skills/frameworks/nextjs/SKILL.md +137 -137
- package/templates/skills/frameworks/nuxt/SKILL.md +50 -50
- package/templates/skills/frameworks/rails/SKILL.md +76 -76
- package/templates/skills/frameworks/react/SKILL.md +48 -48
- package/templates/skills/frameworks/react-native/SKILL.md +57 -57
- package/templates/skills/frameworks/spring/SKILL.md +49 -49
- package/templates/skills/frameworks/symfony/SKILL.md +46 -46
- package/templates/skills/frameworks/vue/SKILL.md +46 -46
- package/templates/skills/frameworks/zend/SKILL.md +45 -45
- package/templates/skills/ides/copilot/SKILL.md +47 -47
- package/templates/skills/ides/cursor/SKILL.md +53 -53
- package/templates/skills/ides/jetbrains-ai/SKILL.md +45 -45
- package/templates/skills/ides/replit/SKILL.md +46 -46
- package/templates/skills/ides/tabnine/SKILL.md +39 -39
- package/templates/skills/ides/vscode/SKILL.md +50 -50
- package/templates/skills/ides/windsurf/SKILL.md +46 -46
- package/templates/skills/ides/zed/SKILL.md +42 -42
- package/templates/skills/languages/c/SKILL.md +343 -343
- package/templates/skills/languages/cpp/SKILL.md +753 -753
- package/templates/skills/languages/csharp/SKILL.md +427 -427
- package/templates/skills/languages/elixir/SKILL.md +464 -464
- package/templates/skills/languages/erlang/SKILL.md +371 -371
- package/templates/skills/languages/go/SKILL.md +655 -655
- package/templates/skills/languages/haskell/SKILL.md +187 -187
- package/templates/skills/languages/java/SKILL.md +617 -617
- package/templates/skills/languages/javascript/SKILL.md +641 -641
- package/templates/skills/languages/julia/SKILL.md +107 -107
- package/templates/skills/languages/kotlin/SKILL.md +521 -521
- package/templates/skills/languages/lisp/SKILL.md +110 -110
- package/templates/skills/languages/lua/SKILL.md +84 -84
- package/templates/skills/languages/objectivec/SKILL.md +100 -100
- package/templates/skills/languages/php/SKILL.md +426 -426
- package/templates/skills/languages/python/SKILL.md +692 -692
- package/templates/skills/languages/ruby/SKILL.md +431 -431
- package/templates/skills/languages/rust/SKILL.md +487 -487
- package/templates/skills/languages/sas/SKILL.md +83 -83
- package/templates/skills/languages/scala/SKILL.md +358 -358
- package/templates/skills/languages/solidity/SKILL.md +590 -590
- package/templates/skills/languages/sql/SKILL.md +147 -147
- package/templates/skills/languages/swift/SKILL.md +476 -476
- package/templates/skills/languages/typescript/SKILL.md +302 -302
- package/templates/skills/languages/zig/SKILL.md +275 -275
- package/templates/skills/modules/atlassian/SKILL.md +265 -265
- package/templates/skills/modules/context7/SKILL.md +64 -64
- package/templates/skills/modules/figma/SKILL.md +277 -277
- package/templates/skills/modules/github-mcp/SKILL.md +74 -74
- package/templates/skills/modules/grafana/SKILL.md +338 -338
- package/templates/skills/modules/memory/SKILL.md +73 -73
- package/templates/skills/modules/notion/SKILL.md +257 -257
- package/templates/skills/modules/playwright/SKILL.md +100 -100
- package/templates/skills/modules/rulebook-mcp/SKILL.md +166 -166
- package/templates/skills/modules/serena/SKILL.md +347 -347
- package/templates/skills/modules/supabase/SKILL.md +233 -233
- package/templates/skills/modules/synap/SKILL.md +79 -79
- package/templates/skills/modules/vectorizer/SKILL.md +73 -73
- package/templates/skills/services/azure-blob/SKILL.md +194 -194
- package/templates/skills/services/cassandra/SKILL.md +249 -249
- package/templates/skills/services/dynamodb/SKILL.md +318 -318
- package/templates/skills/services/elasticsearch/SKILL.md +357 -357
- package/templates/skills/services/gcs/SKILL.md +188 -188
- package/templates/skills/services/influxdb/SKILL.md +275 -275
- package/templates/skills/services/kafka/SKILL.md +351 -351
- package/templates/skills/services/mariadb/SKILL.md +193 -193
- package/templates/skills/services/memcached/SKILL.md +252 -252
- package/templates/skills/services/minio/SKILL.md +211 -211
- package/templates/skills/services/mongodb/SKILL.md +278 -278
- package/templates/skills/services/mysql/SKILL.md +368 -368
- package/templates/skills/services/neo4j/SKILL.md +257 -257
- package/templates/skills/services/oracle/SKILL.md +300 -300
- package/templates/skills/services/postgresql/SKILL.md +336 -336
- package/templates/skills/services/rabbitmq/SKILL.md +296 -296
- package/templates/skills/services/redis/SKILL.md +302 -302
- package/templates/skills/services/s3/SKILL.md +308 -308
- package/templates/skills/services/sqlite/SKILL.md +304 -304
- package/templates/skills/services/sqlserver/SKILL.md +304 -304
- package/templates/skills/workflows/ralph/SKILL.md +309 -309
- package/templates/skills/workflows/ralph/install.sh +87 -87
- package/templates/skills/workflows/ralph/manifest.json +158 -158
|
@@ -1,728 +1,728 @@
|
|
|
1
|
-
# GitHub Actions Workflows
|
|
2
|
-
|
|
3
|
-
This template provides guidance for implementing GitHub Actions CI/CD workflows with best practices for matrix builds, caching, and automation.
|
|
4
|
-
|
|
5
|
-
## Purpose
|
|
6
|
-
|
|
7
|
-
GitHub Actions workflows automate:
|
|
8
|
-
- Continuous Integration (build, test, lint)
|
|
9
|
-
- Continuous Deployment (publish, deploy)
|
|
10
|
-
- Code quality checks
|
|
11
|
-
- Security scanning
|
|
12
|
-
- Release automation
|
|
13
|
-
- Cross-platform testing
|
|
14
|
-
|
|
15
|
-
## Agent Automation Commands
|
|
16
|
-
|
|
17
|
-
When implementing or modifying GitHub Actions:
|
|
18
|
-
|
|
19
|
-
### Local Testing
|
|
20
|
-
```bash
|
|
21
|
-
# Install act for local testing
|
|
22
|
-
brew install act # macOS
|
|
23
|
-
# or
|
|
24
|
-
choco install act # Windows
|
|
25
|
-
|
|
26
|
-
# Run workflow locally
|
|
27
|
-
act
|
|
28
|
-
|
|
29
|
-
# Run specific job
|
|
30
|
-
act -j test
|
|
31
|
-
|
|
32
|
-
# Run with secrets
|
|
33
|
-
act -s GITHUB_TOKEN=xxx
|
|
34
|
-
```
|
|
35
|
-
|
|
36
|
-
### Workflow Management
|
|
37
|
-
```bash
|
|
38
|
-
# List workflows
|
|
39
|
-
gh workflow list
|
|
40
|
-
|
|
41
|
-
# View workflow runs
|
|
42
|
-
gh run list
|
|
43
|
-
|
|
44
|
-
# View specific run
|
|
45
|
-
gh run view <run-id>
|
|
46
|
-
|
|
47
|
-
# Re-run failed jobs
|
|
48
|
-
gh run rerun <run-id>
|
|
49
|
-
```
|
|
50
|
-
|
|
51
|
-
## Basic Workflow Structure
|
|
52
|
-
|
|
53
|
-
### Minimal CI Workflow
|
|
54
|
-
|
|
55
|
-
**`.github/workflows/ci.yml`**:
|
|
56
|
-
```yaml
|
|
57
|
-
name: CI
|
|
58
|
-
|
|
59
|
-
on:
|
|
60
|
-
push:
|
|
61
|
-
branches: [main, develop]
|
|
62
|
-
pull_request:
|
|
63
|
-
branches: [main, develop]
|
|
64
|
-
|
|
65
|
-
jobs:
|
|
66
|
-
test:
|
|
67
|
-
runs-on: ubuntu-latest
|
|
68
|
-
|
|
69
|
-
steps:
|
|
70
|
-
- uses: actions/checkout@v4
|
|
71
|
-
|
|
72
|
-
- name: Setup Node.js
|
|
73
|
-
uses: actions/setup-node@v4
|
|
74
|
-
with:
|
|
75
|
-
node-version: '20'
|
|
76
|
-
cache: 'npm'
|
|
77
|
-
|
|
78
|
-
- name: Install dependencies
|
|
79
|
-
run: npm ci
|
|
80
|
-
|
|
81
|
-
- name: Run lint
|
|
82
|
-
run: npm run lint
|
|
83
|
-
|
|
84
|
-
- name: Run tests
|
|
85
|
-
run: npm test
|
|
86
|
-
|
|
87
|
-
- name: Build
|
|
88
|
-
run: npm run build
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
### Complete CI/CD Workflow
|
|
92
|
-
|
|
93
|
-
**`.github/workflows/ci-cd.yml`**:
|
|
94
|
-
```yaml
|
|
95
|
-
name: CI/CD
|
|
96
|
-
|
|
97
|
-
on:
|
|
98
|
-
push:
|
|
99
|
-
branches: [main, develop]
|
|
100
|
-
tags: ['v*']
|
|
101
|
-
pull_request:
|
|
102
|
-
branches: [main]
|
|
103
|
-
|
|
104
|
-
env:
|
|
105
|
-
NODE_VERSION: '20'
|
|
106
|
-
|
|
107
|
-
jobs:
|
|
108
|
-
lint:
|
|
109
|
-
name: Lint
|
|
110
|
-
runs-on: ubuntu-latest
|
|
111
|
-
|
|
112
|
-
steps:
|
|
113
|
-
- uses: actions/checkout@v4
|
|
114
|
-
|
|
115
|
-
- name: Setup Node.js
|
|
116
|
-
uses: actions/setup-node@v4
|
|
117
|
-
with:
|
|
118
|
-
node-version: ${{ env.NODE_VERSION }}
|
|
119
|
-
cache: 'npm'
|
|
120
|
-
|
|
121
|
-
- name: Install dependencies
|
|
122
|
-
run: npm ci
|
|
123
|
-
|
|
124
|
-
- name: Run ESLint
|
|
125
|
-
run: npm run lint
|
|
126
|
-
|
|
127
|
-
- name: Run Prettier
|
|
128
|
-
run: npm run format:check
|
|
129
|
-
|
|
130
|
-
test:
|
|
131
|
-
name: Test (Node ${{ matrix.node-version }}, ${{ matrix.os }})
|
|
132
|
-
runs-on: ${{ matrix.os }}
|
|
133
|
-
|
|
134
|
-
strategy:
|
|
135
|
-
matrix:
|
|
136
|
-
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
137
|
-
node-version: ['18', '20', '22']
|
|
138
|
-
fail-fast: false
|
|
139
|
-
|
|
140
|
-
steps:
|
|
141
|
-
- uses: actions/checkout@v4
|
|
142
|
-
|
|
143
|
-
- name: Setup Node.js ${{ matrix.node-version }}
|
|
144
|
-
uses: actions/setup-node@v4
|
|
145
|
-
with:
|
|
146
|
-
node-version: ${{ matrix.node-version }}
|
|
147
|
-
cache: 'npm'
|
|
148
|
-
|
|
149
|
-
- name: Install dependencies
|
|
150
|
-
run: npm ci
|
|
151
|
-
|
|
152
|
-
- name: Run tests
|
|
153
|
-
run: npm test
|
|
154
|
-
|
|
155
|
-
- name: Upload coverage
|
|
156
|
-
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '20'
|
|
157
|
-
uses: codecov/codecov-action@v4
|
|
158
|
-
with:
|
|
159
|
-
token: ${{ secrets.CODECOV_TOKEN }}
|
|
160
|
-
files: ./coverage/lcov.info
|
|
161
|
-
|
|
162
|
-
build:
|
|
163
|
-
name: Build
|
|
164
|
-
runs-on: ubuntu-latest
|
|
165
|
-
needs: [lint, test]
|
|
166
|
-
|
|
167
|
-
steps:
|
|
168
|
-
- uses: actions/checkout@v4
|
|
169
|
-
|
|
170
|
-
- name: Setup Node.js
|
|
171
|
-
uses: actions/setup-node@v4
|
|
172
|
-
with:
|
|
173
|
-
node-version: ${{ env.NODE_VERSION }}
|
|
174
|
-
cache: 'npm'
|
|
175
|
-
|
|
176
|
-
- name: Install dependencies
|
|
177
|
-
run: npm ci
|
|
178
|
-
|
|
179
|
-
- name: Build
|
|
180
|
-
run: npm run build
|
|
181
|
-
|
|
182
|
-
- name: Upload artifacts
|
|
183
|
-
uses: actions/upload-artifact@v4
|
|
184
|
-
with:
|
|
185
|
-
name: dist
|
|
186
|
-
path: dist/
|
|
187
|
-
retention-days: 7
|
|
188
|
-
|
|
189
|
-
publish:
|
|
190
|
-
name: Publish to npm
|
|
191
|
-
runs-on: ubuntu-latest
|
|
192
|
-
needs: [build]
|
|
193
|
-
if: startsWith(github.ref, 'refs/tags/v')
|
|
194
|
-
|
|
195
|
-
steps:
|
|
196
|
-
- uses: actions/checkout@v4
|
|
197
|
-
|
|
198
|
-
- name: Setup Node.js
|
|
199
|
-
uses: actions/setup-node@v4
|
|
200
|
-
with:
|
|
201
|
-
node-version: ${{ env.NODE_VERSION }}
|
|
202
|
-
registry-url: 'https://registry.npmjs.org'
|
|
203
|
-
cache: 'npm'
|
|
204
|
-
|
|
205
|
-
- name: Install dependencies
|
|
206
|
-
run: npm ci
|
|
207
|
-
|
|
208
|
-
- name: Build
|
|
209
|
-
run: npm run build
|
|
210
|
-
|
|
211
|
-
- name: Publish to npm
|
|
212
|
-
run: npm publish --access public
|
|
213
|
-
env:
|
|
214
|
-
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
|
|
215
|
-
```
|
|
216
|
-
|
|
217
|
-
## Best Practices
|
|
218
|
-
|
|
219
|
-
### ✅ DO
|
|
220
|
-
|
|
221
|
-
1. **Use Dependency Caching**
|
|
222
|
-
```yaml
|
|
223
|
-
- uses: actions/setup-node@v4
|
|
224
|
-
with:
|
|
225
|
-
node-version: '20'
|
|
226
|
-
cache: 'npm' # or 'pnpm', 'yarn'
|
|
227
|
-
```
|
|
228
|
-
|
|
229
|
-
2. **Use Matrix Builds for Cross-Platform Testing**
|
|
230
|
-
```yaml
|
|
231
|
-
strategy:
|
|
232
|
-
matrix:
|
|
233
|
-
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
234
|
-
node-version: ['18', '20', '22']
|
|
235
|
-
```
|
|
236
|
-
|
|
237
|
-
3. **Use `needs` for Job Dependencies**
|
|
238
|
-
```yaml
|
|
239
|
-
jobs:
|
|
240
|
-
test:
|
|
241
|
-
# ...
|
|
242
|
-
deploy:
|
|
243
|
-
needs: test # Only runs if test succeeds
|
|
244
|
-
```
|
|
245
|
-
|
|
246
|
-
4. **Use Conditional Execution**
|
|
247
|
-
```yaml
|
|
248
|
-
- name: Publish
|
|
249
|
-
if: github.ref == 'refs/heads/main'
|
|
250
|
-
run: npm publish
|
|
251
|
-
```
|
|
252
|
-
|
|
253
|
-
5. **Pin Action Versions**
|
|
254
|
-
```yaml
|
|
255
|
-
# Good - specific commit SHA
|
|
256
|
-
- uses: actions/checkout@8e5e7e5ab8b370d6c329ec480221332ada57f0ab # v4.1.1
|
|
257
|
-
|
|
258
|
-
# Better - major version (gets patches)
|
|
259
|
-
- uses: actions/checkout@v4
|
|
260
|
-
|
|
261
|
-
# Bad - latest (unpredictable)
|
|
262
|
-
- uses: actions/checkout@main
|
|
263
|
-
```
|
|
264
|
-
|
|
265
|
-
6. **Use Environment Variables**
|
|
266
|
-
```yaml
|
|
267
|
-
env:
|
|
268
|
-
NODE_VERSION: '20'
|
|
269
|
-
DATABASE_URL: ${{ secrets.DATABASE_URL }}
|
|
270
|
-
```
|
|
271
|
-
|
|
272
|
-
### ❌ DON'T
|
|
273
|
-
|
|
274
|
-
1. **Don't hardcode secrets**
|
|
275
|
-
```yaml
|
|
276
|
-
# Bad
|
|
277
|
-
env:
|
|
278
|
-
API_KEY: 'sk_live_abc123'
|
|
279
|
-
|
|
280
|
-
# Good
|
|
281
|
-
env:
|
|
282
|
-
API_KEY: ${{ secrets.API_KEY }}
|
|
283
|
-
```
|
|
284
|
-
|
|
285
|
-
2. **Don't use `latest` for OS**
|
|
286
|
-
```yaml
|
|
287
|
-
# Bad
|
|
288
|
-
runs-on: ubuntu-latest
|
|
289
|
-
|
|
290
|
-
# Better (predictable)
|
|
291
|
-
runs-on: ubuntu-22.04
|
|
292
|
-
```
|
|
293
|
-
|
|
294
|
-
3. **Don't install dependencies twice**
|
|
295
|
-
```yaml
|
|
296
|
-
# Bad - npm install in multiple jobs without artifacts
|
|
297
|
-
|
|
298
|
-
# Good - use artifacts or caching
|
|
299
|
-
```
|
|
300
|
-
|
|
301
|
-
4. **Don't ignore failed jobs**
|
|
302
|
-
```yaml
|
|
303
|
-
# Bad
|
|
304
|
-
continue-on-error: true
|
|
305
|
-
|
|
306
|
-
# Good - fix the underlying issue
|
|
307
|
-
```
|
|
308
|
-
|
|
309
|
-
## Matrix Builds
|
|
310
|
-
|
|
311
|
-
### Language Versions
|
|
312
|
-
|
|
313
|
-
**Node.js**:
|
|
314
|
-
```yaml
|
|
315
|
-
strategy:
|
|
316
|
-
matrix:
|
|
317
|
-
node-version: ['18', '20', '22']
|
|
318
|
-
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
319
|
-
|
|
320
|
-
steps:
|
|
321
|
-
- uses: actions/setup-node@v4
|
|
322
|
-
with:
|
|
323
|
-
node-version: ${{ matrix.node-version }}
|
|
324
|
-
```
|
|
325
|
-
|
|
326
|
-
**Python**:
|
|
327
|
-
```yaml
|
|
328
|
-
strategy:
|
|
329
|
-
matrix:
|
|
330
|
-
python-version: ['3.9', '3.10', '3.11', '3.12']
|
|
331
|
-
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
332
|
-
|
|
333
|
-
steps:
|
|
334
|
-
- uses: actions/setup-python@v5
|
|
335
|
-
with:
|
|
336
|
-
python-version: ${{ matrix.python-version }}
|
|
337
|
-
```
|
|
338
|
-
|
|
339
|
-
**Rust**:
|
|
340
|
-
```yaml
|
|
341
|
-
strategy:
|
|
342
|
-
matrix:
|
|
343
|
-
rust-version: [stable, beta, nightly]
|
|
344
|
-
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
345
|
-
|
|
346
|
-
steps:
|
|
347
|
-
- uses: dtolnay/rust-toolchain@master
|
|
348
|
-
with:
|
|
349
|
-
toolchain: ${{ matrix.rust-version }}
|
|
350
|
-
```
|
|
351
|
-
|
|
352
|
-
### Include/Exclude Matrix Items
|
|
353
|
-
|
|
354
|
-
```yaml
|
|
355
|
-
strategy:
|
|
356
|
-
matrix:
|
|
357
|
-
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
358
|
-
node-version: ['18', '20', '22']
|
|
359
|
-
include:
|
|
360
|
-
# Add experimental combination
|
|
361
|
-
- os: ubuntu-latest
|
|
362
|
-
node-version: '23'
|
|
363
|
-
experimental: true
|
|
364
|
-
exclude:
|
|
365
|
-
# Skip specific combination
|
|
366
|
-
- os: macos-latest
|
|
367
|
-
node-version: '18'
|
|
368
|
-
```
|
|
369
|
-
|
|
370
|
-
## Caching Strategies
|
|
371
|
-
|
|
372
|
-
### npm/pnpm/yarn Cache
|
|
373
|
-
|
|
374
|
-
**Automatic** (recommended):
|
|
375
|
-
```yaml
|
|
376
|
-
- uses: actions/setup-node@v4
|
|
377
|
-
with:
|
|
378
|
-
node-version: '20'
|
|
379
|
-
cache: 'npm' # Automatically caches node_modules
|
|
380
|
-
```
|
|
381
|
-
|
|
382
|
-
**Manual** (advanced):
|
|
383
|
-
```yaml
|
|
384
|
-
- name: Cache node_modules
|
|
385
|
-
uses: actions/cache@v4
|
|
386
|
-
with:
|
|
387
|
-
path: node_modules
|
|
388
|
-
key: ${{ runner.os }}-node-${{ hashFiles('**/package-lock.json') }}
|
|
389
|
-
restore-keys: |
|
|
390
|
-
${{ runner.os }}-node-
|
|
391
|
-
```
|
|
392
|
-
|
|
393
|
-
### Build Artifact Caching
|
|
394
|
-
|
|
395
|
-
```yaml
|
|
396
|
-
- name: Cache build
|
|
397
|
-
uses: actions/cache@v4
|
|
398
|
-
with:
|
|
399
|
-
path: |
|
|
400
|
-
dist/
|
|
401
|
-
.cache/
|
|
402
|
-
key: ${{ runner.os }}-build-${{ hashFiles('src/**') }}
|
|
403
|
-
```
|
|
404
|
-
|
|
405
|
-
### Rust Caching
|
|
406
|
-
|
|
407
|
-
```yaml
|
|
408
|
-
- uses: Swatinem/rust-cache@v2
|
|
409
|
-
with:
|
|
410
|
-
shared-key: "rust-cache"
|
|
411
|
-
cache-on-failure: true
|
|
412
|
-
```
|
|
413
|
-
|
|
414
|
-
## Artifacts and Outputs
|
|
415
|
-
|
|
416
|
-
### Upload Artifacts
|
|
417
|
-
|
|
418
|
-
```yaml
|
|
419
|
-
- name: Build
|
|
420
|
-
run: npm run build
|
|
421
|
-
|
|
422
|
-
- name: Upload build artifacts
|
|
423
|
-
uses: actions/upload-artifact@v4
|
|
424
|
-
with:
|
|
425
|
-
name: dist-${{ github.sha }}
|
|
426
|
-
path: dist/
|
|
427
|
-
retention-days: 7
|
|
428
|
-
if-no-files-found: error
|
|
429
|
-
```
|
|
430
|
-
|
|
431
|
-
### Download Artifacts
|
|
432
|
-
|
|
433
|
-
```yaml
|
|
434
|
-
- name: Download artifacts
|
|
435
|
-
uses: actions/download-artifact@v4
|
|
436
|
-
with:
|
|
437
|
-
name: dist-${{ github.sha }}
|
|
438
|
-
path: dist/
|
|
439
|
-
```
|
|
440
|
-
|
|
441
|
-
### Job Outputs
|
|
442
|
-
|
|
443
|
-
```yaml
|
|
444
|
-
jobs:
|
|
445
|
-
build:
|
|
446
|
-
outputs:
|
|
447
|
-
version: ${{ steps.version.outputs.version }}
|
|
448
|
-
steps:
|
|
449
|
-
- id: version
|
|
450
|
-
run: echo "version=$(node -p "require('./package.json').version")" >> $GITHUB_OUTPUT
|
|
451
|
-
|
|
452
|
-
deploy:
|
|
453
|
-
needs: build
|
|
454
|
-
steps:
|
|
455
|
-
- name: Deploy version ${{ needs.build.outputs.version }}
|
|
456
|
-
run: deploy.sh ${{ needs.build.outputs.version }}
|
|
457
|
-
```
|
|
458
|
-
|
|
459
|
-
## Secrets Management
|
|
460
|
-
|
|
461
|
-
### Using Secrets
|
|
462
|
-
|
|
463
|
-
```yaml
|
|
464
|
-
- name: Deploy
|
|
465
|
-
run: ./deploy.sh
|
|
466
|
-
env:
|
|
467
|
-
API_KEY: ${{ secrets.API_KEY }}
|
|
468
|
-
DATABASE_URL: ${{ secrets.DATABASE_URL }}
|
|
469
|
-
```
|
|
470
|
-
|
|
471
|
-
### Organization Secrets
|
|
472
|
-
|
|
473
|
-
```yaml
|
|
474
|
-
# Available to all repos in org
|
|
475
|
-
- name: Use org secret
|
|
476
|
-
env:
|
|
477
|
-
ORG_SECRET: ${{ secrets.ORG_SECRET }}
|
|
478
|
-
```
|
|
479
|
-
|
|
480
|
-
### Environment Secrets
|
|
481
|
-
|
|
482
|
-
```yaml
|
|
483
|
-
jobs:
|
|
484
|
-
deploy:
|
|
485
|
-
environment: production # Uses production environment secrets
|
|
486
|
-
steps:
|
|
487
|
-
- name: Deploy
|
|
488
|
-
env:
|
|
489
|
-
API_KEY: ${{ secrets.PRODUCTION_API_KEY }}
|
|
490
|
-
```
|
|
491
|
-
|
|
492
|
-
## Conditional Execution
|
|
493
|
-
|
|
494
|
-
### Branch Conditions
|
|
495
|
-
|
|
496
|
-
```yaml
|
|
497
|
-
# Only on main
|
|
498
|
-
- if: github.ref == 'refs/heads/main'
|
|
499
|
-
run: deploy.sh
|
|
500
|
-
|
|
501
|
-
# Not on main
|
|
502
|
-
- if: github.ref != 'refs/heads/main'
|
|
503
|
-
run: echo "Not main branch"
|
|
504
|
-
|
|
505
|
-
# Only on tags
|
|
506
|
-
- if: startsWith(github.ref, 'refs/tags/v')
|
|
507
|
-
run: release.sh
|
|
508
|
-
```
|
|
509
|
-
|
|
510
|
-
### Event Conditions
|
|
511
|
-
|
|
512
|
-
```yaml
|
|
513
|
-
# Only on push (not PR)
|
|
514
|
-
- if: github.event_name == 'push'
|
|
515
|
-
run: deploy.sh
|
|
516
|
-
|
|
517
|
-
# Only on PR
|
|
518
|
-
- if: github.event_name == 'pull_request'
|
|
519
|
-
run: preview.sh
|
|
520
|
-
```
|
|
521
|
-
|
|
522
|
-
### Matrix Conditions
|
|
523
|
-
|
|
524
|
-
```yaml
|
|
525
|
-
# Only on specific OS
|
|
526
|
-
- if: runner.os == 'Linux'
|
|
527
|
-
run: linux-specific-command
|
|
528
|
-
|
|
529
|
-
# Only on specific node version
|
|
530
|
-
- if: matrix.node-version == '20'
|
|
531
|
-
run: upload-coverage.sh
|
|
532
|
-
```
|
|
533
|
-
|
|
534
|
-
## Advanced Patterns
|
|
535
|
-
|
|
536
|
-
### Parallel Jobs with Artifacts
|
|
537
|
-
|
|
538
|
-
```yaml
|
|
539
|
-
jobs:
|
|
540
|
-
build:
|
|
541
|
-
strategy:
|
|
542
|
-
matrix:
|
|
543
|
-
target: [linux, windows, macos]
|
|
544
|
-
steps:
|
|
545
|
-
- run: build-${{ matrix.target }}
|
|
546
|
-
- uses: actions/upload-artifact@v4
|
|
547
|
-
with:
|
|
548
|
-
name: build-${{ matrix.target }}
|
|
549
|
-
path: dist/
|
|
550
|
-
|
|
551
|
-
test:
|
|
552
|
-
needs: build
|
|
553
|
-
strategy:
|
|
554
|
-
matrix:
|
|
555
|
-
target: [linux, windows, macos]
|
|
556
|
-
steps:
|
|
557
|
-
- uses: actions/download-artifact@v4
|
|
558
|
-
with:
|
|
559
|
-
name: build-${{ matrix.target }}
|
|
560
|
-
- run: test.sh
|
|
561
|
-
```
|
|
562
|
-
|
|
563
|
-
### Reusable Workflows
|
|
564
|
-
|
|
565
|
-
**`.github/workflows/reusable-test.yml`**:
|
|
566
|
-
```yaml
|
|
567
|
-
name: Reusable Test Workflow
|
|
568
|
-
|
|
569
|
-
on:
|
|
570
|
-
workflow_call:
|
|
571
|
-
inputs:
|
|
572
|
-
node-version:
|
|
573
|
-
required: true
|
|
574
|
-
type: string
|
|
575
|
-
|
|
576
|
-
jobs:
|
|
577
|
-
test:
|
|
578
|
-
runs-on: ubuntu-latest
|
|
579
|
-
steps:
|
|
580
|
-
- uses: actions/checkout@v4
|
|
581
|
-
- uses: actions/setup-node@v4
|
|
582
|
-
with:
|
|
583
|
-
node-version: ${{ inputs.node-version }}
|
|
584
|
-
- run: npm ci
|
|
585
|
-
- run: npm test
|
|
586
|
-
```
|
|
587
|
-
|
|
588
|
-
**Calling reusable workflow**:
|
|
589
|
-
```yaml
|
|
590
|
-
jobs:
|
|
591
|
-
test-node-18:
|
|
592
|
-
uses: ./.github/workflows/reusable-test.yml
|
|
593
|
-
with:
|
|
594
|
-
node-version: '18'
|
|
595
|
-
|
|
596
|
-
test-node-20:
|
|
597
|
-
uses: ./.github/workflows/reusable-test.yml
|
|
598
|
-
with:
|
|
599
|
-
node-version: '20'
|
|
600
|
-
```
|
|
601
|
-
|
|
602
|
-
### Dynamic Matrix from JSON
|
|
603
|
-
|
|
604
|
-
```yaml
|
|
605
|
-
jobs:
|
|
606
|
-
generate-matrix:
|
|
607
|
-
outputs:
|
|
608
|
-
matrix: ${{ steps.set-matrix.outputs.matrix }}
|
|
609
|
-
steps:
|
|
610
|
-
- id: set-matrix
|
|
611
|
-
run: echo "matrix={\"node\":[\"18\",\"20\",\"22\"]}" >> $GITHUB_OUTPUT
|
|
612
|
-
|
|
613
|
-
test:
|
|
614
|
-
needs: generate-matrix
|
|
615
|
-
strategy:
|
|
616
|
-
matrix: ${{ fromJson(needs.generate-matrix.outputs.matrix) }}
|
|
617
|
-
steps:
|
|
618
|
-
- run: test-node-${{ matrix.node }}
|
|
619
|
-
```
|
|
620
|
-
|
|
621
|
-
## Security Best Practices
|
|
622
|
-
|
|
623
|
-
### Pull Request Security
|
|
624
|
-
|
|
625
|
-
```yaml
|
|
626
|
-
on:
|
|
627
|
-
pull_request_target: # Has write access to repo
|
|
628
|
-
types: [opened, synchronize]
|
|
629
|
-
|
|
630
|
-
jobs:
|
|
631
|
-
test:
|
|
632
|
-
# Only run for trusted contributors
|
|
633
|
-
if: github.event.pull_request.head.repo.full_name == github.repository
|
|
634
|
-
steps:
|
|
635
|
-
- uses: actions/checkout@v4
|
|
636
|
-
with:
|
|
637
|
-
ref: ${{ github.event.pull_request.head.sha }}
|
|
638
|
-
```
|
|
639
|
-
|
|
640
|
-
### Least Privilege Permissions
|
|
641
|
-
|
|
642
|
-
```yaml
|
|
643
|
-
permissions:
|
|
644
|
-
contents: read
|
|
645
|
-
pull-requests: write
|
|
646
|
-
issues: write
|
|
647
|
-
|
|
648
|
-
jobs:
|
|
649
|
-
test:
|
|
650
|
-
permissions:
|
|
651
|
-
contents: read # Override with minimal permissions
|
|
652
|
-
steps:
|
|
653
|
-
- uses: actions/checkout@v4
|
|
654
|
-
```
|
|
655
|
-
|
|
656
|
-
### GITHUB_TOKEN Scope
|
|
657
|
-
|
|
658
|
-
```yaml
|
|
659
|
-
- name: Create release
|
|
660
|
-
uses: actions/create-release@v1
|
|
661
|
-
env:
|
|
662
|
-
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Automatically scoped
|
|
663
|
-
```
|
|
664
|
-
|
|
665
|
-
## Troubleshooting
|
|
666
|
-
|
|
667
|
-
### Workflow Not Triggering
|
|
668
|
-
|
|
669
|
-
**Check**:
|
|
670
|
-
1. YAML syntax valid (`yamllint .github/workflows/`)
|
|
671
|
-
2. Branch/path filters correct
|
|
672
|
-
3. Workflow file in `.github/workflows/`
|
|
673
|
-
4. Workflow enabled in repo settings
|
|
674
|
-
|
|
675
|
-
### Cache Not Restoring
|
|
676
|
-
|
|
677
|
-
**Solutions**:
|
|
678
|
-
1. Check cache key uniqueness
|
|
679
|
-
2. Verify path exists
|
|
680
|
-
3. Check cache size limits (10GB max)
|
|
681
|
-
4. Use `restore-keys` for fallback
|
|
682
|
-
|
|
683
|
-
### Job Timeout
|
|
684
|
-
|
|
685
|
-
**Increase timeout**:
|
|
686
|
-
```yaml
|
|
687
|
-
jobs:
|
|
688
|
-
test:
|
|
689
|
-
timeout-minutes: 60 # Default is 360
|
|
690
|
-
```
|
|
691
|
-
|
|
692
|
-
### Debugging
|
|
693
|
-
|
|
694
|
-
**Enable debug logging**:
|
|
695
|
-
```yaml
|
|
696
|
-
- name: Debug
|
|
697
|
-
run: |
|
|
698
|
-
echo "Event: ${{ github.event_name }}"
|
|
699
|
-
echo "Ref: ${{ github.ref }}"
|
|
700
|
-
echo "SHA: ${{ github.sha }}"
|
|
701
|
-
```
|
|
702
|
-
|
|
703
|
-
## Common Pitfalls
|
|
704
|
-
|
|
705
|
-
1. **❌ Not caching dependencies**: Slow CI builds
|
|
706
|
-
2. **❌ Running tests sequentially**: Use matrix for parallel
|
|
707
|
-
3. **❌ Hardcoding versions**: Use environment variables
|
|
708
|
-
4. **❌ No timeout limits**: Jobs hang indefinitely
|
|
709
|
-
5. **❌ Exposing secrets**: Use `secrets` context properly
|
|
710
|
-
6. **❌ Not pinning action versions**: Unpredictable behavior
|
|
711
|
-
|
|
712
|
-
## Integration with Rulebook
|
|
713
|
-
|
|
714
|
-
If using `@hivehub/rulebook`, workflows are automatically generated:
|
|
715
|
-
|
|
716
|
-
```bash
|
|
717
|
-
# Generate workflows
|
|
718
|
-
npx @hivehub/rulebook workflows
|
|
719
|
-
|
|
720
|
-
# Creates language-specific workflows in .github/workflows/
|
|
721
|
-
```
|
|
722
|
-
|
|
723
|
-
## Related Templates
|
|
724
|
-
|
|
725
|
-
- See `/.rulebook/specs/CI_CD_PATTERNS.md` for common CI/CD patterns
|
|
726
|
-
- See `/.rulebook/specs/SECRETS_MANAGEMENT.md` for secrets handling
|
|
727
|
-
- See `/.rulebook/specs/QUALITY_ENFORCEMENT.md` for quality gates
|
|
728
|
-
- See language-specific templates for test/build commands
|
|
1
|
+
# GitHub Actions Workflows
|
|
2
|
+
|
|
3
|
+
This template provides guidance for implementing GitHub Actions CI/CD workflows with best practices for matrix builds, caching, and automation.
|
|
4
|
+
|
|
5
|
+
## Purpose
|
|
6
|
+
|
|
7
|
+
GitHub Actions workflows automate:
|
|
8
|
+
- Continuous Integration (build, test, lint)
|
|
9
|
+
- Continuous Deployment (publish, deploy)
|
|
10
|
+
- Code quality checks
|
|
11
|
+
- Security scanning
|
|
12
|
+
- Release automation
|
|
13
|
+
- Cross-platform testing
|
|
14
|
+
|
|
15
|
+
## Agent Automation Commands
|
|
16
|
+
|
|
17
|
+
When implementing or modifying GitHub Actions:
|
|
18
|
+
|
|
19
|
+
### Local Testing
|
|
20
|
+
```bash
|
|
21
|
+
# Install act for local testing
|
|
22
|
+
brew install act # macOS
|
|
23
|
+
# or
|
|
24
|
+
choco install act # Windows
|
|
25
|
+
|
|
26
|
+
# Run workflow locally
|
|
27
|
+
act
|
|
28
|
+
|
|
29
|
+
# Run specific job
|
|
30
|
+
act -j test
|
|
31
|
+
|
|
32
|
+
# Run with secrets
|
|
33
|
+
act -s GITHUB_TOKEN=xxx
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
### Workflow Management
|
|
37
|
+
```bash
|
|
38
|
+
# List workflows
|
|
39
|
+
gh workflow list
|
|
40
|
+
|
|
41
|
+
# View workflow runs
|
|
42
|
+
gh run list
|
|
43
|
+
|
|
44
|
+
# View specific run
|
|
45
|
+
gh run view <run-id>
|
|
46
|
+
|
|
47
|
+
# Re-run failed jobs
|
|
48
|
+
gh run rerun <run-id>
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
## Basic Workflow Structure
|
|
52
|
+
|
|
53
|
+
### Minimal CI Workflow
|
|
54
|
+
|
|
55
|
+
**`.github/workflows/ci.yml`**:
|
|
56
|
+
```yaml
|
|
57
|
+
name: CI
|
|
58
|
+
|
|
59
|
+
on:
|
|
60
|
+
push:
|
|
61
|
+
branches: [main, develop]
|
|
62
|
+
pull_request:
|
|
63
|
+
branches: [main, develop]
|
|
64
|
+
|
|
65
|
+
jobs:
|
|
66
|
+
test:
|
|
67
|
+
runs-on: ubuntu-latest
|
|
68
|
+
|
|
69
|
+
steps:
|
|
70
|
+
- uses: actions/checkout@v4
|
|
71
|
+
|
|
72
|
+
- name: Setup Node.js
|
|
73
|
+
uses: actions/setup-node@v4
|
|
74
|
+
with:
|
|
75
|
+
node-version: '20'
|
|
76
|
+
cache: 'npm'
|
|
77
|
+
|
|
78
|
+
- name: Install dependencies
|
|
79
|
+
run: npm ci
|
|
80
|
+
|
|
81
|
+
- name: Run lint
|
|
82
|
+
run: npm run lint
|
|
83
|
+
|
|
84
|
+
- name: Run tests
|
|
85
|
+
run: npm test
|
|
86
|
+
|
|
87
|
+
- name: Build
|
|
88
|
+
run: npm run build
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
### Complete CI/CD Workflow
|
|
92
|
+
|
|
93
|
+
**`.github/workflows/ci-cd.yml`**:
|
|
94
|
+
```yaml
|
|
95
|
+
name: CI/CD
|
|
96
|
+
|
|
97
|
+
on:
|
|
98
|
+
push:
|
|
99
|
+
branches: [main, develop]
|
|
100
|
+
tags: ['v*']
|
|
101
|
+
pull_request:
|
|
102
|
+
branches: [main]
|
|
103
|
+
|
|
104
|
+
env:
|
|
105
|
+
NODE_VERSION: '20'
|
|
106
|
+
|
|
107
|
+
jobs:
|
|
108
|
+
lint:
|
|
109
|
+
name: Lint
|
|
110
|
+
runs-on: ubuntu-latest
|
|
111
|
+
|
|
112
|
+
steps:
|
|
113
|
+
- uses: actions/checkout@v4
|
|
114
|
+
|
|
115
|
+
- name: Setup Node.js
|
|
116
|
+
uses: actions/setup-node@v4
|
|
117
|
+
with:
|
|
118
|
+
node-version: ${{ env.NODE_VERSION }}
|
|
119
|
+
cache: 'npm'
|
|
120
|
+
|
|
121
|
+
- name: Install dependencies
|
|
122
|
+
run: npm ci
|
|
123
|
+
|
|
124
|
+
- name: Run ESLint
|
|
125
|
+
run: npm run lint
|
|
126
|
+
|
|
127
|
+
- name: Run Prettier
|
|
128
|
+
run: npm run format:check
|
|
129
|
+
|
|
130
|
+
test:
|
|
131
|
+
name: Test (Node ${{ matrix.node-version }}, ${{ matrix.os }})
|
|
132
|
+
runs-on: ${{ matrix.os }}
|
|
133
|
+
|
|
134
|
+
strategy:
|
|
135
|
+
matrix:
|
|
136
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
137
|
+
node-version: ['18', '20', '22']
|
|
138
|
+
fail-fast: false
|
|
139
|
+
|
|
140
|
+
steps:
|
|
141
|
+
- uses: actions/checkout@v4
|
|
142
|
+
|
|
143
|
+
- name: Setup Node.js ${{ matrix.node-version }}
|
|
144
|
+
uses: actions/setup-node@v4
|
|
145
|
+
with:
|
|
146
|
+
node-version: ${{ matrix.node-version }}
|
|
147
|
+
cache: 'npm'
|
|
148
|
+
|
|
149
|
+
- name: Install dependencies
|
|
150
|
+
run: npm ci
|
|
151
|
+
|
|
152
|
+
- name: Run tests
|
|
153
|
+
run: npm test
|
|
154
|
+
|
|
155
|
+
- name: Upload coverage
|
|
156
|
+
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '20'
|
|
157
|
+
uses: codecov/codecov-action@v4
|
|
158
|
+
with:
|
|
159
|
+
token: ${{ secrets.CODECOV_TOKEN }}
|
|
160
|
+
files: ./coverage/lcov.info
|
|
161
|
+
|
|
162
|
+
build:
|
|
163
|
+
name: Build
|
|
164
|
+
runs-on: ubuntu-latest
|
|
165
|
+
needs: [lint, test]
|
|
166
|
+
|
|
167
|
+
steps:
|
|
168
|
+
- uses: actions/checkout@v4
|
|
169
|
+
|
|
170
|
+
- name: Setup Node.js
|
|
171
|
+
uses: actions/setup-node@v4
|
|
172
|
+
with:
|
|
173
|
+
node-version: ${{ env.NODE_VERSION }}
|
|
174
|
+
cache: 'npm'
|
|
175
|
+
|
|
176
|
+
- name: Install dependencies
|
|
177
|
+
run: npm ci
|
|
178
|
+
|
|
179
|
+
- name: Build
|
|
180
|
+
run: npm run build
|
|
181
|
+
|
|
182
|
+
- name: Upload artifacts
|
|
183
|
+
uses: actions/upload-artifact@v4
|
|
184
|
+
with:
|
|
185
|
+
name: dist
|
|
186
|
+
path: dist/
|
|
187
|
+
retention-days: 7
|
|
188
|
+
|
|
189
|
+
publish:
|
|
190
|
+
name: Publish to npm
|
|
191
|
+
runs-on: ubuntu-latest
|
|
192
|
+
needs: [build]
|
|
193
|
+
if: startsWith(github.ref, 'refs/tags/v')
|
|
194
|
+
|
|
195
|
+
steps:
|
|
196
|
+
- uses: actions/checkout@v4
|
|
197
|
+
|
|
198
|
+
- name: Setup Node.js
|
|
199
|
+
uses: actions/setup-node@v4
|
|
200
|
+
with:
|
|
201
|
+
node-version: ${{ env.NODE_VERSION }}
|
|
202
|
+
registry-url: 'https://registry.npmjs.org'
|
|
203
|
+
cache: 'npm'
|
|
204
|
+
|
|
205
|
+
- name: Install dependencies
|
|
206
|
+
run: npm ci
|
|
207
|
+
|
|
208
|
+
- name: Build
|
|
209
|
+
run: npm run build
|
|
210
|
+
|
|
211
|
+
- name: Publish to npm
|
|
212
|
+
run: npm publish --access public
|
|
213
|
+
env:
|
|
214
|
+
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
## Best Practices
|
|
218
|
+
|
|
219
|
+
### ✅ DO
|
|
220
|
+
|
|
221
|
+
1. **Use Dependency Caching**
|
|
222
|
+
```yaml
|
|
223
|
+
- uses: actions/setup-node@v4
|
|
224
|
+
with:
|
|
225
|
+
node-version: '20'
|
|
226
|
+
cache: 'npm' # or 'pnpm', 'yarn'
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
2. **Use Matrix Builds for Cross-Platform Testing**
|
|
230
|
+
```yaml
|
|
231
|
+
strategy:
|
|
232
|
+
matrix:
|
|
233
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
234
|
+
node-version: ['18', '20', '22']
|
|
235
|
+
```
|
|
236
|
+
|
|
237
|
+
3. **Use `needs` for Job Dependencies**
|
|
238
|
+
```yaml
|
|
239
|
+
jobs:
|
|
240
|
+
test:
|
|
241
|
+
# ...
|
|
242
|
+
deploy:
|
|
243
|
+
needs: test # Only runs if test succeeds
|
|
244
|
+
```
|
|
245
|
+
|
|
246
|
+
4. **Use Conditional Execution**
|
|
247
|
+
```yaml
|
|
248
|
+
- name: Publish
|
|
249
|
+
if: github.ref == 'refs/heads/main'
|
|
250
|
+
run: npm publish
|
|
251
|
+
```
|
|
252
|
+
|
|
253
|
+
5. **Pin Action Versions**
|
|
254
|
+
```yaml
|
|
255
|
+
# Good - specific commit SHA
|
|
256
|
+
- uses: actions/checkout@8e5e7e5ab8b370d6c329ec480221332ada57f0ab # v4.1.1
|
|
257
|
+
|
|
258
|
+
# Better - major version (gets patches)
|
|
259
|
+
- uses: actions/checkout@v4
|
|
260
|
+
|
|
261
|
+
# Bad - latest (unpredictable)
|
|
262
|
+
- uses: actions/checkout@main
|
|
263
|
+
```
|
|
264
|
+
|
|
265
|
+
6. **Use Environment Variables**
|
|
266
|
+
```yaml
|
|
267
|
+
env:
|
|
268
|
+
NODE_VERSION: '20'
|
|
269
|
+
DATABASE_URL: ${{ secrets.DATABASE_URL }}
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
### ❌ DON'T
|
|
273
|
+
|
|
274
|
+
1. **Don't hardcode secrets**
|
|
275
|
+
```yaml
|
|
276
|
+
# Bad
|
|
277
|
+
env:
|
|
278
|
+
API_KEY: 'sk_live_abc123'
|
|
279
|
+
|
|
280
|
+
# Good
|
|
281
|
+
env:
|
|
282
|
+
API_KEY: ${{ secrets.API_KEY }}
|
|
283
|
+
```
|
|
284
|
+
|
|
285
|
+
2. **Don't use `latest` for OS**
|
|
286
|
+
```yaml
|
|
287
|
+
# Bad
|
|
288
|
+
runs-on: ubuntu-latest
|
|
289
|
+
|
|
290
|
+
# Better (predictable)
|
|
291
|
+
runs-on: ubuntu-22.04
|
|
292
|
+
```
|
|
293
|
+
|
|
294
|
+
3. **Don't install dependencies twice**
|
|
295
|
+
```yaml
|
|
296
|
+
# Bad - npm install in multiple jobs without artifacts
|
|
297
|
+
|
|
298
|
+
# Good - use artifacts or caching
|
|
299
|
+
```
|
|
300
|
+
|
|
301
|
+
4. **Don't ignore failed jobs**
|
|
302
|
+
```yaml
|
|
303
|
+
# Bad
|
|
304
|
+
continue-on-error: true
|
|
305
|
+
|
|
306
|
+
# Good - fix the underlying issue
|
|
307
|
+
```
|
|
308
|
+
|
|
309
|
+
## Matrix Builds
|
|
310
|
+
|
|
311
|
+
### Language Versions
|
|
312
|
+
|
|
313
|
+
**Node.js**:
|
|
314
|
+
```yaml
|
|
315
|
+
strategy:
|
|
316
|
+
matrix:
|
|
317
|
+
node-version: ['18', '20', '22']
|
|
318
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
319
|
+
|
|
320
|
+
steps:
|
|
321
|
+
- uses: actions/setup-node@v4
|
|
322
|
+
with:
|
|
323
|
+
node-version: ${{ matrix.node-version }}
|
|
324
|
+
```
|
|
325
|
+
|
|
326
|
+
**Python**:
|
|
327
|
+
```yaml
|
|
328
|
+
strategy:
|
|
329
|
+
matrix:
|
|
330
|
+
python-version: ['3.9', '3.10', '3.11', '3.12']
|
|
331
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
332
|
+
|
|
333
|
+
steps:
|
|
334
|
+
- uses: actions/setup-python@v5
|
|
335
|
+
with:
|
|
336
|
+
python-version: ${{ matrix.python-version }}
|
|
337
|
+
```
|
|
338
|
+
|
|
339
|
+
**Rust**:
|
|
340
|
+
```yaml
|
|
341
|
+
strategy:
|
|
342
|
+
matrix:
|
|
343
|
+
rust-version: [stable, beta, nightly]
|
|
344
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
345
|
+
|
|
346
|
+
steps:
|
|
347
|
+
- uses: dtolnay/rust-toolchain@master
|
|
348
|
+
with:
|
|
349
|
+
toolchain: ${{ matrix.rust-version }}
|
|
350
|
+
```
|
|
351
|
+
|
|
352
|
+
### Include/Exclude Matrix Items
|
|
353
|
+
|
|
354
|
+
```yaml
|
|
355
|
+
strategy:
|
|
356
|
+
matrix:
|
|
357
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
358
|
+
node-version: ['18', '20', '22']
|
|
359
|
+
include:
|
|
360
|
+
# Add experimental combination
|
|
361
|
+
- os: ubuntu-latest
|
|
362
|
+
node-version: '23'
|
|
363
|
+
experimental: true
|
|
364
|
+
exclude:
|
|
365
|
+
# Skip specific combination
|
|
366
|
+
- os: macos-latest
|
|
367
|
+
node-version: '18'
|
|
368
|
+
```
|
|
369
|
+
|
|
370
|
+
## Caching Strategies
|
|
371
|
+
|
|
372
|
+
### npm/pnpm/yarn Cache
|
|
373
|
+
|
|
374
|
+
**Automatic** (recommended):
|
|
375
|
+
```yaml
|
|
376
|
+
- uses: actions/setup-node@v4
|
|
377
|
+
with:
|
|
378
|
+
node-version: '20'
|
|
379
|
+
cache: 'npm' # Automatically caches node_modules
|
|
380
|
+
```
|
|
381
|
+
|
|
382
|
+
**Manual** (advanced):
|
|
383
|
+
```yaml
|
|
384
|
+
- name: Cache node_modules
|
|
385
|
+
uses: actions/cache@v4
|
|
386
|
+
with:
|
|
387
|
+
path: node_modules
|
|
388
|
+
key: ${{ runner.os }}-node-${{ hashFiles('**/package-lock.json') }}
|
|
389
|
+
restore-keys: |
|
|
390
|
+
${{ runner.os }}-node-
|
|
391
|
+
```
|
|
392
|
+
|
|
393
|
+
### Build Artifact Caching
|
|
394
|
+
|
|
395
|
+
```yaml
|
|
396
|
+
- name: Cache build
|
|
397
|
+
uses: actions/cache@v4
|
|
398
|
+
with:
|
|
399
|
+
path: |
|
|
400
|
+
dist/
|
|
401
|
+
.cache/
|
|
402
|
+
key: ${{ runner.os }}-build-${{ hashFiles('src/**') }}
|
|
403
|
+
```
|
|
404
|
+
|
|
405
|
+
### Rust Caching
|
|
406
|
+
|
|
407
|
+
```yaml
|
|
408
|
+
- uses: Swatinem/rust-cache@v2
|
|
409
|
+
with:
|
|
410
|
+
shared-key: "rust-cache"
|
|
411
|
+
cache-on-failure: true
|
|
412
|
+
```
|
|
413
|
+
|
|
414
|
+
## Artifacts and Outputs
|
|
415
|
+
|
|
416
|
+
### Upload Artifacts
|
|
417
|
+
|
|
418
|
+
```yaml
|
|
419
|
+
- name: Build
|
|
420
|
+
run: npm run build
|
|
421
|
+
|
|
422
|
+
- name: Upload build artifacts
|
|
423
|
+
uses: actions/upload-artifact@v4
|
|
424
|
+
with:
|
|
425
|
+
name: dist-${{ github.sha }}
|
|
426
|
+
path: dist/
|
|
427
|
+
retention-days: 7
|
|
428
|
+
if-no-files-found: error
|
|
429
|
+
```
|
|
430
|
+
|
|
431
|
+
### Download Artifacts
|
|
432
|
+
|
|
433
|
+
```yaml
|
|
434
|
+
- name: Download artifacts
|
|
435
|
+
uses: actions/download-artifact@v4
|
|
436
|
+
with:
|
|
437
|
+
name: dist-${{ github.sha }}
|
|
438
|
+
path: dist/
|
|
439
|
+
```
|
|
440
|
+
|
|
441
|
+
### Job Outputs
|
|
442
|
+
|
|
443
|
+
```yaml
|
|
444
|
+
jobs:
|
|
445
|
+
build:
|
|
446
|
+
outputs:
|
|
447
|
+
version: ${{ steps.version.outputs.version }}
|
|
448
|
+
steps:
|
|
449
|
+
- id: version
|
|
450
|
+
run: echo "version=$(node -p "require('./package.json').version")" >> $GITHUB_OUTPUT
|
|
451
|
+
|
|
452
|
+
deploy:
|
|
453
|
+
needs: build
|
|
454
|
+
steps:
|
|
455
|
+
- name: Deploy version ${{ needs.build.outputs.version }}
|
|
456
|
+
run: deploy.sh ${{ needs.build.outputs.version }}
|
|
457
|
+
```
|
|
458
|
+
|
|
459
|
+
## Secrets Management
|
|
460
|
+
|
|
461
|
+
### Using Secrets
|
|
462
|
+
|
|
463
|
+
```yaml
|
|
464
|
+
- name: Deploy
|
|
465
|
+
run: ./deploy.sh
|
|
466
|
+
env:
|
|
467
|
+
API_KEY: ${{ secrets.API_KEY }}
|
|
468
|
+
DATABASE_URL: ${{ secrets.DATABASE_URL }}
|
|
469
|
+
```
|
|
470
|
+
|
|
471
|
+
### Organization Secrets
|
|
472
|
+
|
|
473
|
+
```yaml
|
|
474
|
+
# Available to all repos in org
|
|
475
|
+
- name: Use org secret
|
|
476
|
+
env:
|
|
477
|
+
ORG_SECRET: ${{ secrets.ORG_SECRET }}
|
|
478
|
+
```
|
|
479
|
+
|
|
480
|
+
### Environment Secrets
|
|
481
|
+
|
|
482
|
+
```yaml
|
|
483
|
+
jobs:
|
|
484
|
+
deploy:
|
|
485
|
+
environment: production # Uses production environment secrets
|
|
486
|
+
steps:
|
|
487
|
+
- name: Deploy
|
|
488
|
+
env:
|
|
489
|
+
API_KEY: ${{ secrets.PRODUCTION_API_KEY }}
|
|
490
|
+
```
|
|
491
|
+
|
|
492
|
+
## Conditional Execution
|
|
493
|
+
|
|
494
|
+
### Branch Conditions
|
|
495
|
+
|
|
496
|
+
```yaml
|
|
497
|
+
# Only on main
|
|
498
|
+
- if: github.ref == 'refs/heads/main'
|
|
499
|
+
run: deploy.sh
|
|
500
|
+
|
|
501
|
+
# Not on main
|
|
502
|
+
- if: github.ref != 'refs/heads/main'
|
|
503
|
+
run: echo "Not main branch"
|
|
504
|
+
|
|
505
|
+
# Only on tags
|
|
506
|
+
- if: startsWith(github.ref, 'refs/tags/v')
|
|
507
|
+
run: release.sh
|
|
508
|
+
```
|
|
509
|
+
|
|
510
|
+
### Event Conditions
|
|
511
|
+
|
|
512
|
+
```yaml
|
|
513
|
+
# Only on push (not PR)
|
|
514
|
+
- if: github.event_name == 'push'
|
|
515
|
+
run: deploy.sh
|
|
516
|
+
|
|
517
|
+
# Only on PR
|
|
518
|
+
- if: github.event_name == 'pull_request'
|
|
519
|
+
run: preview.sh
|
|
520
|
+
```
|
|
521
|
+
|
|
522
|
+
### Matrix Conditions
|
|
523
|
+
|
|
524
|
+
```yaml
|
|
525
|
+
# Only on specific OS
|
|
526
|
+
- if: runner.os == 'Linux'
|
|
527
|
+
run: linux-specific-command
|
|
528
|
+
|
|
529
|
+
# Only on specific node version
|
|
530
|
+
- if: matrix.node-version == '20'
|
|
531
|
+
run: upload-coverage.sh
|
|
532
|
+
```
|
|
533
|
+
|
|
534
|
+
## Advanced Patterns
|
|
535
|
+
|
|
536
|
+
### Parallel Jobs with Artifacts
|
|
537
|
+
|
|
538
|
+
```yaml
|
|
539
|
+
jobs:
|
|
540
|
+
build:
|
|
541
|
+
strategy:
|
|
542
|
+
matrix:
|
|
543
|
+
target: [linux, windows, macos]
|
|
544
|
+
steps:
|
|
545
|
+
- run: build-${{ matrix.target }}
|
|
546
|
+
- uses: actions/upload-artifact@v4
|
|
547
|
+
with:
|
|
548
|
+
name: build-${{ matrix.target }}
|
|
549
|
+
path: dist/
|
|
550
|
+
|
|
551
|
+
test:
|
|
552
|
+
needs: build
|
|
553
|
+
strategy:
|
|
554
|
+
matrix:
|
|
555
|
+
target: [linux, windows, macos]
|
|
556
|
+
steps:
|
|
557
|
+
- uses: actions/download-artifact@v4
|
|
558
|
+
with:
|
|
559
|
+
name: build-${{ matrix.target }}
|
|
560
|
+
- run: test.sh
|
|
561
|
+
```
|
|
562
|
+
|
|
563
|
+
### Reusable Workflows
|
|
564
|
+
|
|
565
|
+
**`.github/workflows/reusable-test.yml`**:
|
|
566
|
+
```yaml
|
|
567
|
+
name: Reusable Test Workflow
|
|
568
|
+
|
|
569
|
+
on:
|
|
570
|
+
workflow_call:
|
|
571
|
+
inputs:
|
|
572
|
+
node-version:
|
|
573
|
+
required: true
|
|
574
|
+
type: string
|
|
575
|
+
|
|
576
|
+
jobs:
|
|
577
|
+
test:
|
|
578
|
+
runs-on: ubuntu-latest
|
|
579
|
+
steps:
|
|
580
|
+
- uses: actions/checkout@v4
|
|
581
|
+
- uses: actions/setup-node@v4
|
|
582
|
+
with:
|
|
583
|
+
node-version: ${{ inputs.node-version }}
|
|
584
|
+
- run: npm ci
|
|
585
|
+
- run: npm test
|
|
586
|
+
```
|
|
587
|
+
|
|
588
|
+
**Calling reusable workflow**:
|
|
589
|
+
```yaml
|
|
590
|
+
jobs:
|
|
591
|
+
test-node-18:
|
|
592
|
+
uses: ./.github/workflows/reusable-test.yml
|
|
593
|
+
with:
|
|
594
|
+
node-version: '18'
|
|
595
|
+
|
|
596
|
+
test-node-20:
|
|
597
|
+
uses: ./.github/workflows/reusable-test.yml
|
|
598
|
+
with:
|
|
599
|
+
node-version: '20'
|
|
600
|
+
```
|
|
601
|
+
|
|
602
|
+
### Dynamic Matrix from JSON
|
|
603
|
+
|
|
604
|
+
```yaml
|
|
605
|
+
jobs:
|
|
606
|
+
generate-matrix:
|
|
607
|
+
outputs:
|
|
608
|
+
matrix: ${{ steps.set-matrix.outputs.matrix }}
|
|
609
|
+
steps:
|
|
610
|
+
- id: set-matrix
|
|
611
|
+
run: echo "matrix={\"node\":[\"18\",\"20\",\"22\"]}" >> $GITHUB_OUTPUT
|
|
612
|
+
|
|
613
|
+
test:
|
|
614
|
+
needs: generate-matrix
|
|
615
|
+
strategy:
|
|
616
|
+
matrix: ${{ fromJson(needs.generate-matrix.outputs.matrix) }}
|
|
617
|
+
steps:
|
|
618
|
+
- run: test-node-${{ matrix.node }}
|
|
619
|
+
```
|
|
620
|
+
|
|
621
|
+
## Security Best Practices
|
|
622
|
+
|
|
623
|
+
### Pull Request Security
|
|
624
|
+
|
|
625
|
+
```yaml
|
|
626
|
+
on:
|
|
627
|
+
pull_request_target: # Has write access to repo
|
|
628
|
+
types: [opened, synchronize]
|
|
629
|
+
|
|
630
|
+
jobs:
|
|
631
|
+
test:
|
|
632
|
+
# Only run for trusted contributors
|
|
633
|
+
if: github.event.pull_request.head.repo.full_name == github.repository
|
|
634
|
+
steps:
|
|
635
|
+
- uses: actions/checkout@v4
|
|
636
|
+
with:
|
|
637
|
+
ref: ${{ github.event.pull_request.head.sha }}
|
|
638
|
+
```
|
|
639
|
+
|
|
640
|
+
### Least Privilege Permissions
|
|
641
|
+
|
|
642
|
+
```yaml
|
|
643
|
+
permissions:
|
|
644
|
+
contents: read
|
|
645
|
+
pull-requests: write
|
|
646
|
+
issues: write
|
|
647
|
+
|
|
648
|
+
jobs:
|
|
649
|
+
test:
|
|
650
|
+
permissions:
|
|
651
|
+
contents: read # Override with minimal permissions
|
|
652
|
+
steps:
|
|
653
|
+
- uses: actions/checkout@v4
|
|
654
|
+
```
|
|
655
|
+
|
|
656
|
+
### GITHUB_TOKEN Scope
|
|
657
|
+
|
|
658
|
+
```yaml
|
|
659
|
+
- name: Create release
|
|
660
|
+
uses: actions/create-release@v1
|
|
661
|
+
env:
|
|
662
|
+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Automatically scoped
|
|
663
|
+
```
|
|
664
|
+
|
|
665
|
+
## Troubleshooting
|
|
666
|
+
|
|
667
|
+
### Workflow Not Triggering
|
|
668
|
+
|
|
669
|
+
**Check**:
|
|
670
|
+
1. YAML syntax valid (`yamllint .github/workflows/`)
|
|
671
|
+
2. Branch/path filters correct
|
|
672
|
+
3. Workflow file in `.github/workflows/`
|
|
673
|
+
4. Workflow enabled in repo settings
|
|
674
|
+
|
|
675
|
+
### Cache Not Restoring
|
|
676
|
+
|
|
677
|
+
**Solutions**:
|
|
678
|
+
1. Check cache key uniqueness
|
|
679
|
+
2. Verify path exists
|
|
680
|
+
3. Check cache size limits (10GB max)
|
|
681
|
+
4. Use `restore-keys` for fallback
|
|
682
|
+
|
|
683
|
+
### Job Timeout
|
|
684
|
+
|
|
685
|
+
**Increase timeout**:
|
|
686
|
+
```yaml
|
|
687
|
+
jobs:
|
|
688
|
+
test:
|
|
689
|
+
timeout-minutes: 60 # Default is 360
|
|
690
|
+
```
|
|
691
|
+
|
|
692
|
+
### Debugging
|
|
693
|
+
|
|
694
|
+
**Enable debug logging**:
|
|
695
|
+
```yaml
|
|
696
|
+
- name: Debug
|
|
697
|
+
run: |
|
|
698
|
+
echo "Event: ${{ github.event_name }}"
|
|
699
|
+
echo "Ref: ${{ github.ref }}"
|
|
700
|
+
echo "SHA: ${{ github.sha }}"
|
|
701
|
+
```
|
|
702
|
+
|
|
703
|
+
## Common Pitfalls
|
|
704
|
+
|
|
705
|
+
1. **❌ Not caching dependencies**: Slow CI builds
|
|
706
|
+
2. **❌ Running tests sequentially**: Use matrix for parallel
|
|
707
|
+
3. **❌ Hardcoding versions**: Use environment variables
|
|
708
|
+
4. **❌ No timeout limits**: Jobs hang indefinitely
|
|
709
|
+
5. **❌ Exposing secrets**: Use `secrets` context properly
|
|
710
|
+
6. **❌ Not pinning action versions**: Unpredictable behavior
|
|
711
|
+
|
|
712
|
+
## Integration with Rulebook
|
|
713
|
+
|
|
714
|
+
If using `@hivehub/rulebook`, workflows are automatically generated:
|
|
715
|
+
|
|
716
|
+
```bash
|
|
717
|
+
# Generate workflows
|
|
718
|
+
npx @hivehub/rulebook workflows
|
|
719
|
+
|
|
720
|
+
# Creates language-specific workflows in .github/workflows/
|
|
721
|
+
```
|
|
722
|
+
|
|
723
|
+
## Related Templates
|
|
724
|
+
|
|
725
|
+
- See `/.rulebook/specs/CI_CD_PATTERNS.md` for common CI/CD patterns
|
|
726
|
+
- See `/.rulebook/specs/SECRETS_MANAGEMENT.md` for secrets handling
|
|
727
|
+
- See `/.rulebook/specs/QUALITY_ENFORCEMENT.md` for quality gates
|
|
728
|
+
- See language-specific templates for test/build commands
|