@wazir-dev/cli 1.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/AGENTS.md +111 -0
- package/CHANGELOG.md +14 -0
- package/CONTRIBUTING.md +101 -0
- package/LICENSE +21 -0
- package/README.md +314 -0
- package/assets/composition-engine.mmd +34 -0
- package/assets/demo-script.sh +17 -0
- package/assets/logo-dark.svg +14 -0
- package/assets/logo.svg +14 -0
- package/assets/pipeline.mmd +39 -0
- package/assets/record-demo.sh +51 -0
- package/docs/README.md +51 -0
- package/docs/adapters/context-mode.md +60 -0
- package/docs/concepts/architecture.md +87 -0
- package/docs/concepts/artifact-model.md +60 -0
- package/docs/concepts/composition-engine.md +36 -0
- package/docs/concepts/indexing-and-recall.md +160 -0
- package/docs/concepts/observability.md +41 -0
- package/docs/concepts/roles-and-workflows.md +59 -0
- package/docs/concepts/terminology-policy.md +27 -0
- package/docs/getting-started/01-installation.md +78 -0
- package/docs/getting-started/02-first-run.md +102 -0
- package/docs/getting-started/03-adding-to-project.md +15 -0
- package/docs/getting-started/04-host-setup.md +15 -0
- package/docs/guides/ci-integration.md +15 -0
- package/docs/guides/creating-skills.md +15 -0
- package/docs/guides/expertise-module-authoring.md +15 -0
- package/docs/guides/hook-development.md +15 -0
- package/docs/guides/memory-and-learnings.md +34 -0
- package/docs/guides/multi-host-export.md +15 -0
- package/docs/guides/troubleshooting.md +101 -0
- package/docs/guides/writing-custom-roles.md +15 -0
- package/docs/plans/2026-03-15-cli-pipeline-integration-design.md +592 -0
- package/docs/plans/2026-03-15-cli-pipeline-integration-plan.md +598 -0
- package/docs/plans/2026-03-15-docs-enforcement-plan.md +238 -0
- package/docs/readmes/INDEX.md +99 -0
- package/docs/readmes/features/expertise/README.md +171 -0
- package/docs/readmes/features/exports/README.md +222 -0
- package/docs/readmes/features/hooks/README.md +103 -0
- package/docs/readmes/features/hooks/loop-cap-guard.md +133 -0
- package/docs/readmes/features/hooks/post-tool-capture.md +121 -0
- package/docs/readmes/features/hooks/post-tool-lint.md +130 -0
- package/docs/readmes/features/hooks/pre-compact-summary.md +122 -0
- package/docs/readmes/features/hooks/pre-tool-capture-route.md +100 -0
- package/docs/readmes/features/hooks/protected-path-write-guard.md +128 -0
- package/docs/readmes/features/hooks/session-start.md +119 -0
- package/docs/readmes/features/hooks/stop-handoff-harvest.md +125 -0
- package/docs/readmes/features/roles/README.md +157 -0
- package/docs/readmes/features/roles/clarifier.md +152 -0
- package/docs/readmes/features/roles/content-author.md +190 -0
- package/docs/readmes/features/roles/designer.md +193 -0
- package/docs/readmes/features/roles/executor.md +184 -0
- package/docs/readmes/features/roles/learner.md +210 -0
- package/docs/readmes/features/roles/planner.md +182 -0
- package/docs/readmes/features/roles/researcher.md +164 -0
- package/docs/readmes/features/roles/reviewer.md +184 -0
- package/docs/readmes/features/roles/specifier.md +162 -0
- package/docs/readmes/features/roles/verifier.md +215 -0
- package/docs/readmes/features/schemas/README.md +178 -0
- package/docs/readmes/features/skills/README.md +63 -0
- package/docs/readmes/features/skills/brainstorming.md +96 -0
- package/docs/readmes/features/skills/debugging.md +148 -0
- package/docs/readmes/features/skills/design.md +120 -0
- package/docs/readmes/features/skills/prepare-next.md +109 -0
- package/docs/readmes/features/skills/run-audit.md +159 -0
- package/docs/readmes/features/skills/scan-project.md +109 -0
- package/docs/readmes/features/skills/self-audit.md +176 -0
- package/docs/readmes/features/skills/tdd.md +137 -0
- package/docs/readmes/features/skills/using-skills.md +92 -0
- package/docs/readmes/features/skills/verification.md +120 -0
- package/docs/readmes/features/skills/writing-plans.md +104 -0
- package/docs/readmes/features/tooling/README.md +320 -0
- package/docs/readmes/features/workflows/README.md +186 -0
- package/docs/readmes/features/workflows/author.md +181 -0
- package/docs/readmes/features/workflows/clarify.md +154 -0
- package/docs/readmes/features/workflows/design-review.md +171 -0
- package/docs/readmes/features/workflows/design.md +169 -0
- package/docs/readmes/features/workflows/discover.md +162 -0
- package/docs/readmes/features/workflows/execute.md +173 -0
- package/docs/readmes/features/workflows/learn.md +167 -0
- package/docs/readmes/features/workflows/plan-review.md +165 -0
- package/docs/readmes/features/workflows/plan.md +170 -0
- package/docs/readmes/features/workflows/prepare-next.md +167 -0
- package/docs/readmes/features/workflows/review.md +169 -0
- package/docs/readmes/features/workflows/run-audit.md +191 -0
- package/docs/readmes/features/workflows/spec-challenge.md +159 -0
- package/docs/readmes/features/workflows/specify.md +160 -0
- package/docs/readmes/features/workflows/verify.md +177 -0
- package/docs/readmes/packages/README.md +50 -0
- package/docs/readmes/packages/ajv.md +117 -0
- package/docs/readmes/packages/context-mode.md +118 -0
- package/docs/readmes/packages/gray-matter.md +116 -0
- package/docs/readmes/packages/node-test.md +137 -0
- package/docs/readmes/packages/yaml.md +112 -0
- package/docs/reference/configuration-reference.md +159 -0
- package/docs/reference/expertise-index.md +52 -0
- package/docs/reference/git-flow.md +43 -0
- package/docs/reference/hooks.md +87 -0
- package/docs/reference/host-exports.md +50 -0
- package/docs/reference/launch-checklist.md +172 -0
- package/docs/reference/marketplace-listings.md +76 -0
- package/docs/reference/release-process.md +34 -0
- package/docs/reference/roles-reference.md +77 -0
- package/docs/reference/skills.md +33 -0
- package/docs/reference/templates.md +29 -0
- package/docs/reference/tooling-cli.md +94 -0
- package/docs/truth-claims.yaml +222 -0
- package/expertise/PROGRESS.md +63 -0
- package/expertise/README.md +18 -0
- package/expertise/antipatterns/PROGRESS.md +56 -0
- package/expertise/antipatterns/backend/api-design-antipatterns.md +1271 -0
- package/expertise/antipatterns/backend/auth-antipatterns.md +1195 -0
- package/expertise/antipatterns/backend/caching-antipatterns.md +622 -0
- package/expertise/antipatterns/backend/database-antipatterns.md +1038 -0
- package/expertise/antipatterns/backend/index.md +24 -0
- package/expertise/antipatterns/backend/microservices-antipatterns.md +850 -0
- package/expertise/antipatterns/code/architecture-antipatterns.md +919 -0
- package/expertise/antipatterns/code/async-antipatterns.md +622 -0
- package/expertise/antipatterns/code/code-smells.md +1186 -0
- package/expertise/antipatterns/code/dependency-antipatterns.md +1209 -0
- package/expertise/antipatterns/code/error-handling-antipatterns.md +1360 -0
- package/expertise/antipatterns/code/index.md +27 -0
- package/expertise/antipatterns/code/naming-and-abstraction.md +1118 -0
- package/expertise/antipatterns/code/state-management-antipatterns.md +1076 -0
- package/expertise/antipatterns/code/testing-antipatterns.md +1053 -0
- package/expertise/antipatterns/design/accessibility-antipatterns.md +1136 -0
- package/expertise/antipatterns/design/dark-patterns.md +1121 -0
- package/expertise/antipatterns/design/index.md +22 -0
- package/expertise/antipatterns/design/ui-antipatterns.md +1202 -0
- package/expertise/antipatterns/design/ux-antipatterns.md +680 -0
- package/expertise/antipatterns/frontend/css-layout-antipatterns.md +691 -0
- package/expertise/antipatterns/frontend/flutter-antipatterns.md +1827 -0
- package/expertise/antipatterns/frontend/index.md +23 -0
- package/expertise/antipatterns/frontend/mobile-antipatterns.md +573 -0
- package/expertise/antipatterns/frontend/react-antipatterns.md +1128 -0
- package/expertise/antipatterns/frontend/spa-antipatterns.md +1235 -0
- package/expertise/antipatterns/index.md +31 -0
- package/expertise/antipatterns/performance/index.md +20 -0
- package/expertise/antipatterns/performance/performance-antipatterns.md +1013 -0
- package/expertise/antipatterns/performance/premature-optimization.md +623 -0
- package/expertise/antipatterns/performance/scaling-antipatterns.md +785 -0
- package/expertise/antipatterns/process/ai-coding-antipatterns.md +853 -0
- package/expertise/antipatterns/process/code-review-antipatterns.md +656 -0
- package/expertise/antipatterns/process/deployment-antipatterns.md +920 -0
- package/expertise/antipatterns/process/index.md +23 -0
- package/expertise/antipatterns/process/technical-debt-antipatterns.md +647 -0
- package/expertise/antipatterns/security/index.md +20 -0
- package/expertise/antipatterns/security/secrets-antipatterns.md +849 -0
- package/expertise/antipatterns/security/security-theater.md +843 -0
- package/expertise/antipatterns/security/vulnerability-patterns.md +801 -0
- package/expertise/architecture/PROGRESS.md +70 -0
- package/expertise/architecture/data/caching-architecture.md +671 -0
- package/expertise/architecture/data/data-consistency.md +574 -0
- package/expertise/architecture/data/data-modeling.md +536 -0
- package/expertise/architecture/data/event-streams-and-queues.md +634 -0
- package/expertise/architecture/data/index.md +25 -0
- package/expertise/architecture/data/search-architecture.md +663 -0
- package/expertise/architecture/data/sql-vs-nosql.md +708 -0
- package/expertise/architecture/decisions/architecture-decision-records.md +640 -0
- package/expertise/architecture/decisions/build-vs-buy.md +616 -0
- package/expertise/architecture/decisions/index.md +23 -0
- package/expertise/architecture/decisions/monolith-to-microservices.md +790 -0
- package/expertise/architecture/decisions/technology-selection.md +616 -0
- package/expertise/architecture/distributed/cap-theorem-and-tradeoffs.md +800 -0
- package/expertise/architecture/distributed/circuit-breaker-bulkhead.md +741 -0
- package/expertise/architecture/distributed/consensus-and-coordination.md +796 -0
- package/expertise/architecture/distributed/distributed-systems-fundamentals.md +564 -0
- package/expertise/architecture/distributed/idempotency-and-retry.md +796 -0
- package/expertise/architecture/distributed/index.md +25 -0
- package/expertise/architecture/distributed/saga-pattern.md +797 -0
- package/expertise/architecture/foundations/architectural-thinking.md +460 -0
- package/expertise/architecture/foundations/coupling-and-cohesion.md +770 -0
- package/expertise/architecture/foundations/design-principles-solid.md +649 -0
- package/expertise/architecture/foundations/domain-driven-design.md +719 -0
- package/expertise/architecture/foundations/index.md +25 -0
- package/expertise/architecture/foundations/separation-of-concerns.md +472 -0
- package/expertise/architecture/foundations/twelve-factor-app.md +797 -0
- package/expertise/architecture/index.md +34 -0
- package/expertise/architecture/integration/api-design-graphql.md +638 -0
- package/expertise/architecture/integration/api-design-grpc.md +804 -0
- package/expertise/architecture/integration/api-design-rest.md +892 -0
- package/expertise/architecture/integration/index.md +25 -0
- package/expertise/architecture/integration/third-party-integration.md +795 -0
- package/expertise/architecture/integration/webhooks-and-callbacks.md +1152 -0
- package/expertise/architecture/integration/websockets-realtime.md +791 -0
- package/expertise/architecture/mobile-architecture/index.md +22 -0
- package/expertise/architecture/mobile-architecture/mobile-app-architecture.md +780 -0
- package/expertise/architecture/mobile-architecture/mobile-backend-for-frontend.md +670 -0
- package/expertise/architecture/mobile-architecture/offline-first.md +719 -0
- package/expertise/architecture/mobile-architecture/push-and-sync.md +782 -0
- package/expertise/architecture/patterns/cqrs-event-sourcing.md +717 -0
- package/expertise/architecture/patterns/event-driven.md +797 -0
- package/expertise/architecture/patterns/hexagonal-clean-architecture.md +870 -0
- package/expertise/architecture/patterns/index.md +27 -0
- package/expertise/architecture/patterns/layered-architecture.md +736 -0
- package/expertise/architecture/patterns/microservices.md +753 -0
- package/expertise/architecture/patterns/modular-monolith.md +692 -0
- package/expertise/architecture/patterns/monolith.md +626 -0
- package/expertise/architecture/patterns/plugin-architecture.md +735 -0
- package/expertise/architecture/patterns/serverless.md +780 -0
- package/expertise/architecture/scaling/database-scaling.md +615 -0
- package/expertise/architecture/scaling/feature-flags-and-rollouts.md +757 -0
- package/expertise/architecture/scaling/horizontal-vs-vertical.md +606 -0
- package/expertise/architecture/scaling/index.md +24 -0
- package/expertise/architecture/scaling/multi-tenancy.md +800 -0
- package/expertise/architecture/scaling/stateless-design.md +787 -0
- package/expertise/backend/embedded-firmware.md +625 -0
- package/expertise/backend/go.md +853 -0
- package/expertise/backend/index.md +24 -0
- package/expertise/backend/java-spring.md +448 -0
- package/expertise/backend/node-typescript.md +625 -0
- package/expertise/backend/python-fastapi.md +724 -0
- package/expertise/backend/rust.md +458 -0
- package/expertise/backend/solidity.md +711 -0
- package/expertise/composition-map.yaml +443 -0
- package/expertise/content/foundations/content-modeling.md +395 -0
- package/expertise/content/foundations/editorial-standards.md +449 -0
- package/expertise/content/foundations/index.md +24 -0
- package/expertise/content/foundations/microcopy.md +455 -0
- package/expertise/content/foundations/terminology-governance.md +509 -0
- package/expertise/content/index.md +34 -0
- package/expertise/content/patterns/accessibility-copy.md +518 -0
- package/expertise/content/patterns/index.md +24 -0
- package/expertise/content/patterns/notification-content.md +433 -0
- package/expertise/content/patterns/sample-content.md +486 -0
- package/expertise/content/patterns/state-copy.md +439 -0
- package/expertise/design/PROGRESS.md +58 -0
- package/expertise/design/disciplines/dark-mode-theming.md +577 -0
- package/expertise/design/disciplines/design-systems.md +595 -0
- package/expertise/design/disciplines/index.md +25 -0
- package/expertise/design/disciplines/information-architecture.md +800 -0
- package/expertise/design/disciplines/interaction-design.md +788 -0
- package/expertise/design/disciplines/responsive-design.md +552 -0
- package/expertise/design/disciplines/usability-testing.md +516 -0
- package/expertise/design/disciplines/user-research.md +792 -0
- package/expertise/design/foundations/accessibility-design.md +796 -0
- package/expertise/design/foundations/color-theory.md +797 -0
- package/expertise/design/foundations/iconography.md +795 -0
- package/expertise/design/foundations/index.md +26 -0
- package/expertise/design/foundations/motion-and-animation.md +653 -0
- package/expertise/design/foundations/rtl-design.md +585 -0
- package/expertise/design/foundations/spacing-and-layout.md +607 -0
- package/expertise/design/foundations/typography.md +800 -0
- package/expertise/design/foundations/visual-hierarchy.md +761 -0
- package/expertise/design/index.md +32 -0
- package/expertise/design/patterns/authentication-flows.md +474 -0
- package/expertise/design/patterns/content-consumption.md +789 -0
- package/expertise/design/patterns/data-display.md +618 -0
- package/expertise/design/patterns/e-commerce.md +1494 -0
- package/expertise/design/patterns/feedback-and-states.md +642 -0
- package/expertise/design/patterns/forms-and-input.md +819 -0
- package/expertise/design/patterns/gamification.md +801 -0
- package/expertise/design/patterns/index.md +31 -0
- package/expertise/design/patterns/microinteractions.md +449 -0
- package/expertise/design/patterns/navigation.md +800 -0
- package/expertise/design/patterns/notifications.md +705 -0
- package/expertise/design/patterns/onboarding.md +700 -0
- package/expertise/design/patterns/search-and-filter.md +601 -0
- package/expertise/design/patterns/settings-and-preferences.md +768 -0
- package/expertise/design/patterns/social-and-community.md +748 -0
- package/expertise/design/platforms/desktop-native.md +612 -0
- package/expertise/design/platforms/index.md +25 -0
- package/expertise/design/platforms/mobile-android.md +825 -0
- package/expertise/design/platforms/mobile-cross-platform.md +983 -0
- package/expertise/design/platforms/mobile-ios.md +699 -0
- package/expertise/design/platforms/tablet.md +794 -0
- package/expertise/design/platforms/web-dashboard.md +790 -0
- package/expertise/design/platforms/web-responsive.md +550 -0
- package/expertise/design/psychology/behavioral-nudges.md +449 -0
- package/expertise/design/psychology/cognitive-load.md +1191 -0
- package/expertise/design/psychology/error-psychology.md +778 -0
- package/expertise/design/psychology/index.md +22 -0
- package/expertise/design/psychology/persuasive-design.md +736 -0
- package/expertise/design/psychology/user-mental-models.md +623 -0
- package/expertise/design/tooling/open-pencil.md +266 -0
- package/expertise/frontend/angular.md +1073 -0
- package/expertise/frontend/desktop-electron.md +546 -0
- package/expertise/frontend/flutter.md +782 -0
- package/expertise/frontend/index.md +27 -0
- package/expertise/frontend/native-android.md +409 -0
- package/expertise/frontend/native-ios.md +490 -0
- package/expertise/frontend/react-native.md +1160 -0
- package/expertise/frontend/react.md +808 -0
- package/expertise/frontend/vue.md +1089 -0
- package/expertise/humanize/domain-rules-code.md +79 -0
- package/expertise/humanize/domain-rules-content.md +67 -0
- package/expertise/humanize/domain-rules-technical-docs.md +56 -0
- package/expertise/humanize/index.md +35 -0
- package/expertise/humanize/self-audit-checklist.md +87 -0
- package/expertise/humanize/sentence-patterns.md +218 -0
- package/expertise/humanize/vocabulary-blacklist.md +105 -0
- package/expertise/i18n/PROGRESS.md +65 -0
- package/expertise/i18n/advanced/accessibility-and-i18n.md +28 -0
- package/expertise/i18n/advanced/bidirectional-text-algorithm.md +38 -0
- package/expertise/i18n/advanced/complex-scripts.md +30 -0
- package/expertise/i18n/advanced/performance-and-i18n.md +27 -0
- package/expertise/i18n/advanced/testing-i18n.md +28 -0
- package/expertise/i18n/content/content-adaptation.md +23 -0
- package/expertise/i18n/content/locale-specific-formatting.md +23 -0
- package/expertise/i18n/content/machine-translation-integration.md +28 -0
- package/expertise/i18n/content/translation-management.md +29 -0
- package/expertise/i18n/foundations/date-time-calendars.md +67 -0
- package/expertise/i18n/foundations/i18n-architecture.md +272 -0
- package/expertise/i18n/foundations/locale-and-language-tags.md +79 -0
- package/expertise/i18n/foundations/numbers-currency-units.md +61 -0
- package/expertise/i18n/foundations/pluralization-and-gender.md +109 -0
- package/expertise/i18n/foundations/string-externalization.md +236 -0
- package/expertise/i18n/foundations/text-direction-bidi.md +241 -0
- package/expertise/i18n/foundations/unicode-and-encoding.md +86 -0
- package/expertise/i18n/index.md +38 -0
- package/expertise/i18n/platform/backend-i18n.md +31 -0
- package/expertise/i18n/platform/flutter-i18n.md +148 -0
- package/expertise/i18n/platform/native-android-i18n.md +36 -0
- package/expertise/i18n/platform/native-ios-i18n.md +36 -0
- package/expertise/i18n/platform/react-i18n.md +103 -0
- package/expertise/i18n/platform/web-css-i18n.md +81 -0
- package/expertise/i18n/rtl/arabic-specific.md +175 -0
- package/expertise/i18n/rtl/hebrew-specific.md +149 -0
- package/expertise/i18n/rtl/rtl-animations-and-transitions.md +111 -0
- package/expertise/i18n/rtl/rtl-forms-and-input.md +161 -0
- package/expertise/i18n/rtl/rtl-fundamentals.md +211 -0
- package/expertise/i18n/rtl/rtl-icons-and-images.md +181 -0
- package/expertise/i18n/rtl/rtl-layout-mirroring.md +252 -0
- package/expertise/i18n/rtl/rtl-navigation-and-gestures.md +107 -0
- package/expertise/i18n/rtl/rtl-testing-and-qa.md +147 -0
- package/expertise/i18n/rtl/rtl-typography.md +160 -0
- package/expertise/index.md +113 -0
- package/expertise/index.yaml +216 -0
- package/expertise/infrastructure/cloud-aws.md +597 -0
- package/expertise/infrastructure/cloud-gcp.md +599 -0
- package/expertise/infrastructure/cybersecurity.md +816 -0
- package/expertise/infrastructure/database-mongodb.md +447 -0
- package/expertise/infrastructure/database-postgres.md +400 -0
- package/expertise/infrastructure/devops-cicd.md +787 -0
- package/expertise/infrastructure/index.md +27 -0
- package/expertise/performance/PROGRESS.md +50 -0
- package/expertise/performance/backend/api-latency.md +1204 -0
- package/expertise/performance/backend/background-jobs.md +506 -0
- package/expertise/performance/backend/connection-pooling.md +1209 -0
- package/expertise/performance/backend/database-query-optimization.md +515 -0
- package/expertise/performance/backend/index.md +23 -0
- package/expertise/performance/backend/rate-limiting-and-throttling.md +971 -0
- package/expertise/performance/foundations/algorithmic-complexity.md +954 -0
- package/expertise/performance/foundations/caching-strategies.md +489 -0
- package/expertise/performance/foundations/concurrency-and-parallelism.md +847 -0
- package/expertise/performance/foundations/index.md +24 -0
- package/expertise/performance/foundations/measuring-and-profiling.md +440 -0
- package/expertise/performance/foundations/memory-management.md +964 -0
- package/expertise/performance/foundations/performance-budgets.md +1314 -0
- package/expertise/performance/index.md +31 -0
- package/expertise/performance/infrastructure/auto-scaling.md +1059 -0
- package/expertise/performance/infrastructure/cdn-and-edge.md +1081 -0
- package/expertise/performance/infrastructure/index.md +22 -0
- package/expertise/performance/infrastructure/load-balancing.md +1081 -0
- package/expertise/performance/infrastructure/observability.md +1079 -0
- package/expertise/performance/mobile/index.md +23 -0
- package/expertise/performance/mobile/mobile-animations.md +544 -0
- package/expertise/performance/mobile/mobile-memory-battery.md +416 -0
- package/expertise/performance/mobile/mobile-network.md +452 -0
- package/expertise/performance/mobile/mobile-rendering.md +599 -0
- package/expertise/performance/mobile/mobile-startup-time.md +505 -0
- package/expertise/performance/platform-specific/flutter-performance.md +647 -0
- package/expertise/performance/platform-specific/index.md +22 -0
- package/expertise/performance/platform-specific/node-performance.md +1307 -0
- package/expertise/performance/platform-specific/postgres-performance.md +1366 -0
- package/expertise/performance/platform-specific/react-performance.md +1403 -0
- package/expertise/performance/web/bundle-optimization.md +1239 -0
- package/expertise/performance/web/image-and-media.md +636 -0
- package/expertise/performance/web/index.md +24 -0
- package/expertise/performance/web/network-optimization.md +1133 -0
- package/expertise/performance/web/rendering-performance.md +1098 -0
- package/expertise/performance/web/ssr-and-hydration.md +918 -0
- package/expertise/performance/web/web-vitals.md +1374 -0
- package/expertise/quality/accessibility.md +985 -0
- package/expertise/quality/evidence-based-verification.md +499 -0
- package/expertise/quality/index.md +24 -0
- package/expertise/quality/ml-model-audit.md +614 -0
- package/expertise/quality/performance.md +600 -0
- package/expertise/quality/testing-api.md +891 -0
- package/expertise/quality/testing-mobile.md +496 -0
- package/expertise/quality/testing-web.md +849 -0
- package/expertise/security/PROGRESS.md +54 -0
- package/expertise/security/agentic-identity.md +540 -0
- package/expertise/security/compliance-frameworks.md +601 -0
- package/expertise/security/data/data-encryption.md +364 -0
- package/expertise/security/data/data-privacy-gdpr.md +692 -0
- package/expertise/security/data/database-security.md +1171 -0
- package/expertise/security/data/index.md +22 -0
- package/expertise/security/data/pii-handling.md +531 -0
- package/expertise/security/foundations/authentication.md +1041 -0
- package/expertise/security/foundations/authorization.md +603 -0
- package/expertise/security/foundations/cryptography.md +1001 -0
- package/expertise/security/foundations/index.md +25 -0
- package/expertise/security/foundations/owasp-top-10.md +1354 -0
- package/expertise/security/foundations/secrets-management.md +1217 -0
- package/expertise/security/foundations/secure-sdlc.md +700 -0
- package/expertise/security/foundations/supply-chain-security.md +698 -0
- package/expertise/security/index.md +31 -0
- package/expertise/security/infrastructure/cloud-security-aws.md +1296 -0
- package/expertise/security/infrastructure/cloud-security-gcp.md +1376 -0
- package/expertise/security/infrastructure/container-security.md +721 -0
- package/expertise/security/infrastructure/incident-response.md +1295 -0
- package/expertise/security/infrastructure/index.md +24 -0
- package/expertise/security/infrastructure/logging-and-monitoring.md +1618 -0
- package/expertise/security/infrastructure/network-security.md +1337 -0
- package/expertise/security/mobile/index.md +23 -0
- package/expertise/security/mobile/mobile-android-security.md +1218 -0
- package/expertise/security/mobile/mobile-binary-protection.md +1229 -0
- package/expertise/security/mobile/mobile-data-storage.md +1265 -0
- package/expertise/security/mobile/mobile-ios-security.md +1401 -0
- package/expertise/security/mobile/mobile-network-security.md +1520 -0
- package/expertise/security/smart-contract-security.md +594 -0
- package/expertise/security/testing/index.md +22 -0
- package/expertise/security/testing/penetration-testing.md +1258 -0
- package/expertise/security/testing/security-code-review.md +1765 -0
- package/expertise/security/testing/threat-modeling.md +1074 -0
- package/expertise/security/testing/vulnerability-scanning.md +1062 -0
- package/expertise/security/web/api-security.md +586 -0
- package/expertise/security/web/cors-and-headers.md +433 -0
- package/expertise/security/web/csrf.md +562 -0
- package/expertise/security/web/file-upload.md +1477 -0
- package/expertise/security/web/index.md +25 -0
- package/expertise/security/web/injection.md +1375 -0
- package/expertise/security/web/session-management.md +1101 -0
- package/expertise/security/web/xss.md +1158 -0
- package/exports/README.md +17 -0
- package/exports/hosts/claude/.claude/agents/clarifier.md +42 -0
- package/exports/hosts/claude/.claude/agents/content-author.md +63 -0
- package/exports/hosts/claude/.claude/agents/designer.md +55 -0
- package/exports/hosts/claude/.claude/agents/executor.md +55 -0
- package/exports/hosts/claude/.claude/agents/learner.md +51 -0
- package/exports/hosts/claude/.claude/agents/planner.md +53 -0
- package/exports/hosts/claude/.claude/agents/researcher.md +43 -0
- package/exports/hosts/claude/.claude/agents/reviewer.md +54 -0
- package/exports/hosts/claude/.claude/agents/specifier.md +47 -0
- package/exports/hosts/claude/.claude/agents/verifier.md +71 -0
- package/exports/hosts/claude/.claude/commands/author.md +42 -0
- package/exports/hosts/claude/.claude/commands/clarify.md +38 -0
- package/exports/hosts/claude/.claude/commands/design-review.md +46 -0
- package/exports/hosts/claude/.claude/commands/design.md +44 -0
- package/exports/hosts/claude/.claude/commands/discover.md +37 -0
- package/exports/hosts/claude/.claude/commands/execute.md +48 -0
- package/exports/hosts/claude/.claude/commands/learn.md +38 -0
- package/exports/hosts/claude/.claude/commands/plan-review.md +42 -0
- package/exports/hosts/claude/.claude/commands/plan.md +39 -0
- package/exports/hosts/claude/.claude/commands/prepare-next.md +37 -0
- package/exports/hosts/claude/.claude/commands/review.md +40 -0
- package/exports/hosts/claude/.claude/commands/run-audit.md +41 -0
- package/exports/hosts/claude/.claude/commands/spec-challenge.md +41 -0
- package/exports/hosts/claude/.claude/commands/specify.md +38 -0
- package/exports/hosts/claude/.claude/commands/verify.md +37 -0
- package/exports/hosts/claude/.claude/settings.json +34 -0
- package/exports/hosts/claude/CLAUDE.md +19 -0
- package/exports/hosts/claude/export.manifest.json +38 -0
- package/exports/hosts/claude/host-package.json +67 -0
- package/exports/hosts/codex/AGENTS.md +19 -0
- package/exports/hosts/codex/export.manifest.json +38 -0
- package/exports/hosts/codex/host-package.json +41 -0
- package/exports/hosts/cursor/.cursor/hooks.json +16 -0
- package/exports/hosts/cursor/.cursor/rules/wazir-core.mdc +19 -0
- package/exports/hosts/cursor/export.manifest.json +38 -0
- package/exports/hosts/cursor/host-package.json +42 -0
- package/exports/hosts/gemini/GEMINI.md +19 -0
- package/exports/hosts/gemini/export.manifest.json +38 -0
- package/exports/hosts/gemini/host-package.json +41 -0
- package/hooks/README.md +18 -0
- package/hooks/definitions/loop_cap_guard.yaml +21 -0
- package/hooks/definitions/post_tool_capture.yaml +24 -0
- package/hooks/definitions/pre_compact_summary.yaml +19 -0
- package/hooks/definitions/pre_tool_capture_route.yaml +19 -0
- package/hooks/definitions/protected_path_write_guard.yaml +19 -0
- package/hooks/definitions/session_start.yaml +19 -0
- package/hooks/definitions/stop_handoff_harvest.yaml +20 -0
- package/hooks/loop-cap-guard +17 -0
- package/hooks/post-tool-lint +36 -0
- package/hooks/protected-path-write-guard +17 -0
- package/hooks/session-start +41 -0
- package/llms-full.txt +2355 -0
- package/llms.txt +43 -0
- package/package.json +79 -0
- package/roles/README.md +20 -0
- package/roles/clarifier.md +42 -0
- package/roles/content-author.md +63 -0
- package/roles/designer.md +55 -0
- package/roles/executor.md +55 -0
- package/roles/learner.md +51 -0
- package/roles/planner.md +53 -0
- package/roles/researcher.md +43 -0
- package/roles/reviewer.md +54 -0
- package/roles/specifier.md +47 -0
- package/roles/verifier.md +71 -0
- package/schemas/README.md +24 -0
- package/schemas/accepted-learning.schema.json +20 -0
- package/schemas/author-artifact.schema.json +156 -0
- package/schemas/clarification.schema.json +19 -0
- package/schemas/design-artifact.schema.json +80 -0
- package/schemas/docs-claim.schema.json +18 -0
- package/schemas/export-manifest.schema.json +20 -0
- package/schemas/hook.schema.json +67 -0
- package/schemas/host-export-package.schema.json +18 -0
- package/schemas/implementation-plan.schema.json +19 -0
- package/schemas/proposed-learning.schema.json +19 -0
- package/schemas/research.schema.json +18 -0
- package/schemas/review.schema.json +29 -0
- package/schemas/run-manifest.schema.json +18 -0
- package/schemas/spec-challenge.schema.json +18 -0
- package/schemas/spec.schema.json +20 -0
- package/schemas/usage.schema.json +102 -0
- package/schemas/verification-proof.schema.json +29 -0
- package/schemas/wazir-manifest.schema.json +173 -0
- package/skills/README.md +40 -0
- package/skills/brainstorming/SKILL.md +77 -0
- package/skills/debugging/SKILL.md +50 -0
- package/skills/design/SKILL.md +61 -0
- package/skills/dispatching-parallel-agents/SKILL.md +128 -0
- package/skills/executing-plans/SKILL.md +70 -0
- package/skills/finishing-a-development-branch/SKILL.md +169 -0
- package/skills/humanize/SKILL.md +123 -0
- package/skills/init-pipeline/SKILL.md +124 -0
- package/skills/prepare-next/SKILL.md +20 -0
- package/skills/receiving-code-review/SKILL.md +123 -0
- package/skills/requesting-code-review/SKILL.md +105 -0
- package/skills/requesting-code-review/code-reviewer.md +108 -0
- package/skills/run-audit/SKILL.md +197 -0
- package/skills/scan-project/SKILL.md +41 -0
- package/skills/self-audit/SKILL.md +153 -0
- package/skills/subagent-driven-development/SKILL.md +154 -0
- package/skills/subagent-driven-development/code-quality-reviewer-prompt.md +26 -0
- package/skills/subagent-driven-development/implementer-prompt.md +102 -0
- package/skills/subagent-driven-development/spec-reviewer-prompt.md +61 -0
- package/skills/tdd/SKILL.md +23 -0
- package/skills/using-git-worktrees/SKILL.md +163 -0
- package/skills/using-skills/SKILL.md +95 -0
- package/skills/verification/SKILL.md +22 -0
- package/skills/wazir/SKILL.md +463 -0
- package/skills/writing-plans/SKILL.md +30 -0
- package/skills/writing-skills/SKILL.md +157 -0
- package/skills/writing-skills/anthropic-best-practices.md +122 -0
- package/skills/writing-skills/persuasion-principles.md +50 -0
- package/templates/README.md +20 -0
- package/templates/artifacts/README.md +10 -0
- package/templates/artifacts/accepted-learning.md +19 -0
- package/templates/artifacts/accepted-learning.template.json +12 -0
- package/templates/artifacts/author.md +74 -0
- package/templates/artifacts/author.template.json +19 -0
- package/templates/artifacts/clarification.md +21 -0
- package/templates/artifacts/clarification.template.json +12 -0
- package/templates/artifacts/execute-notes.md +19 -0
- package/templates/artifacts/implementation-plan.md +21 -0
- package/templates/artifacts/implementation-plan.template.json +11 -0
- package/templates/artifacts/learning-proposal.md +19 -0
- package/templates/artifacts/next-run-handoff.md +21 -0
- package/templates/artifacts/plan-review.md +19 -0
- package/templates/artifacts/proposed-learning.template.json +12 -0
- package/templates/artifacts/research.md +21 -0
- package/templates/artifacts/research.template.json +12 -0
- package/templates/artifacts/review-findings.md +19 -0
- package/templates/artifacts/review.template.json +11 -0
- package/templates/artifacts/run-manifest.template.json +8 -0
- package/templates/artifacts/spec-challenge.md +19 -0
- package/templates/artifacts/spec-challenge.template.json +11 -0
- package/templates/artifacts/spec.md +21 -0
- package/templates/artifacts/spec.template.json +12 -0
- package/templates/artifacts/verification-proof.md +19 -0
- package/templates/artifacts/verification-proof.template.json +11 -0
- package/templates/examples/accepted-learning.example.json +14 -0
- package/templates/examples/author.example.json +152 -0
- package/templates/examples/clarification.example.json +15 -0
- package/templates/examples/docs-claim.example.json +8 -0
- package/templates/examples/export-manifest.example.json +7 -0
- package/templates/examples/host-export-package.example.json +11 -0
- package/templates/examples/implementation-plan.example.json +17 -0
- package/templates/examples/proposed-learning.example.json +13 -0
- package/templates/examples/research.example.json +15 -0
- package/templates/examples/research.example.md +6 -0
- package/templates/examples/review.example.json +17 -0
- package/templates/examples/run-manifest.example.json +9 -0
- package/templates/examples/spec-challenge.example.json +14 -0
- package/templates/examples/spec.example.json +21 -0
- package/templates/examples/verification-proof.example.json +21 -0
- package/templates/examples/wazir-manifest.example.yaml +65 -0
- package/templates/task-definition-schema.md +99 -0
- package/tooling/README.md +20 -0
- package/tooling/src/adapters/context-mode.js +50 -0
- package/tooling/src/capture/command.js +376 -0
- package/tooling/src/capture/store.js +99 -0
- package/tooling/src/capture/usage.js +270 -0
- package/tooling/src/checks/branches.js +50 -0
- package/tooling/src/checks/brand-truth.js +110 -0
- package/tooling/src/checks/changelog.js +231 -0
- package/tooling/src/checks/command-registry.js +36 -0
- package/tooling/src/checks/commits.js +102 -0
- package/tooling/src/checks/docs-drift.js +103 -0
- package/tooling/src/checks/docs-truth.js +201 -0
- package/tooling/src/checks/runtime-surface.js +156 -0
- package/tooling/src/cli.js +116 -0
- package/tooling/src/command-options.js +56 -0
- package/tooling/src/commands/validate.js +320 -0
- package/tooling/src/doctor/command.js +91 -0
- package/tooling/src/export/command.js +77 -0
- package/tooling/src/export/compiler.js +498 -0
- package/tooling/src/guards/loop-cap-guard.js +52 -0
- package/tooling/src/guards/protected-path-write-guard.js +67 -0
- package/tooling/src/index/command.js +152 -0
- package/tooling/src/index/storage.js +1061 -0
- package/tooling/src/index/summarizers.js +261 -0
- package/tooling/src/loaders.js +18 -0
- package/tooling/src/project-root.js +22 -0
- package/tooling/src/recall/command.js +225 -0
- package/tooling/src/schema-validator.js +30 -0
- package/tooling/src/state-root.js +40 -0
- package/tooling/src/status/command.js +71 -0
- package/wazir.manifest.yaml +135 -0
- package/workflows/README.md +19 -0
- package/workflows/author.md +42 -0
- package/workflows/clarify.md +38 -0
- package/workflows/design-review.md +46 -0
- package/workflows/design.md +44 -0
- package/workflows/discover.md +37 -0
- package/workflows/execute.md +48 -0
- package/workflows/learn.md +38 -0
- package/workflows/plan-review.md +42 -0
- package/workflows/plan.md +39 -0
- package/workflows/prepare-next.md +37 -0
- package/workflows/review.md +40 -0
- package/workflows/run-audit.md +41 -0
- package/workflows/spec-challenge.md +41 -0
- package/workflows/specify.md +38 -0
- package/workflows/verify.md +37 -0
|
@@ -0,0 +1,626 @@
|
|
|
1
|
+
# Monolith Architecture — Architecture Expertise Module
|
|
2
|
+
|
|
3
|
+
> A monolith is a single deployable unit containing all application functionality. Despite being called "legacy" by microservices advocates, a well-structured monolith is often the correct architecture for teams of under 30 developers and products with less than 10M DAU — and sometimes even beyond that.
|
|
4
|
+
|
|
5
|
+
> **Category:** Pattern
|
|
6
|
+
> **Complexity:** Simple
|
|
7
|
+
> **Applies when:** Most new projects, teams under ~30 developers, validated products before scaling
|
|
8
|
+
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
## What This Is (and What It Isn't)
|
|
12
|
+
|
|
13
|
+
### Definition
|
|
14
|
+
|
|
15
|
+
A monolithic application is one where the entire business logic — presentation, service layer, domain logic, and data access — runs inside a single OS process and is deployed as a single unit. All code is compiled together, shares the same memory space, and communicates via direct function calls rather than network hops.
|
|
16
|
+
|
|
17
|
+
### The Three Variants
|
|
18
|
+
|
|
19
|
+
**1. Single-Process Monolith (Classic)**
|
|
20
|
+
One process, one codebase, one database. All modules are compiled into a single artifact (a JAR, a .NET DLL, a Rails app, a Django app). Requests are served in-process. This is the most common starting point for any product.
|
|
21
|
+
|
|
22
|
+
**2. Modular Monolith**
|
|
23
|
+
A single deployable unit with explicitly enforced module boundaries inside the codebase. Modules cannot reach into each other's internals — they communicate through defined interfaces. Shopify's "Shopify Core" Rails application is the canonical example: ~2.8 million lines of code, over 500,000 commits, but partitioned into components via their Packwerk tool that enforces dependency rules at CI time. This is the sweet spot for teams of 20–80 developers on an established product (covered separately in `modular-monolith.md`).
|
|
24
|
+
|
|
25
|
+
**3. Distributed Monolith (Anti-Pattern — The Worst of Both Worlds)**
|
|
26
|
+
Multiple processes/services that are still tightly coupled: they share a database, rely on synchronous call chains, and cannot be deployed independently. This pattern combines all the operational complexity of microservices with all the coupling problems of a poorly structured monolith. If you have to deploy 8 services simultaneously to ship one feature, you have a distributed monolith. Avoid this at all costs.
|
|
27
|
+
|
|
28
|
+
### What a Monolith Is NOT
|
|
29
|
+
|
|
30
|
+
- **Not unstructured**: A well-run monolith has strong internal module boundaries. "Monolith" describes deployment topology, not code quality.
|
|
31
|
+
- **Not legacy**: Every greenfield project starts as a monolith. The question is whether to stay there, and for most products at most stages, the answer is yes.
|
|
32
|
+
- **Not unscalable**: Stack Overflow serves 1.3 billion monthly page views from 9 on-premise web servers running a .NET monolith. Shopify processed hundreds of billions in GMV as a single Rails app. Scale is achieved through caching, connection pooling, read replicas, and horizontal replication of the entire process — not decomposition.
|
|
33
|
+
- **Not unmaintainable**: Maintainability is a function of code structure and discipline, not deployment model. A microservices system with poor discipline is harder to maintain than a well-structured monolith.
|
|
34
|
+
|
|
35
|
+
### Common Misconceptions vs. Reality
|
|
36
|
+
|
|
37
|
+
| Misconception | Reality |
|
|
38
|
+
|---|---|
|
|
39
|
+
| "Monoliths don't scale" | Stack Overflow: 9 servers, 1.3B monthly page views, 450 req/sec per server at 12% CPU |
|
|
40
|
+
| "Monoliths slow down teams" | Only when poorly structured. Basecamp ships to web + iOS + Android + desktop with ~12 engineers |
|
|
41
|
+
| "You'll have to rewrite it" | No — the strangler fig pattern allows incremental extraction without rewrites |
|
|
42
|
+
| "Microservices = modern" | Amazon Prime Video cut infra costs 90% by consolidating a microservices system back into a monolith (2023) |
|
|
43
|
+
| "Monoliths can't support multiple frontends" | Basecamp 3 serves web, iOS, Android, Windows, Mac, and email from one Rails monolith |
|
|
44
|
+
|
|
45
|
+
---
|
|
46
|
+
|
|
47
|
+
## When to Use It
|
|
48
|
+
|
|
49
|
+
The monolith is the correct default. The burden of proof lies with anyone proposing to distribute.
|
|
50
|
+
|
|
51
|
+
### Primary Signals — Use a Monolith
|
|
52
|
+
|
|
53
|
+
**Team size under 30 developers.**
|
|
54
|
+
The coordination overhead of microservices (service contracts, API versioning, distributed tracing, independent deployments, inter-service auth) requires dedicated platform engineering capacity. Below ~30 engineers, you don't have the headcount to absorb that tax. The operational gains from independent deployment don't materialise until you have teams that genuinely need to deploy independently, which requires distinct ownership boundaries, which requires a larger organisation.
|
|
55
|
+
|
|
56
|
+
**Traffic under 5–10M DAU (unless extremely compute-intensive).**
|
|
57
|
+
A single vertically-scaled server with proper caching (Redis, Memcached) handles enormous load. Stack Overflow's SQL cluster of 4 servers handles 10,000+ peak queries/second at 15% CPU. For the vast majority of products, the database connection limit and memory saturation points are far beyond what the team will ever encounter. When you do hit them, horizontal scaling (running multiple instances of the monolith behind a load balancer) is the first answer — not decomposition.
|
|
58
|
+
|
|
59
|
+
**You don't yet know your domain boundaries.**
|
|
60
|
+
This is the most important signal and the most commonly ignored. Microservices demand stable service boundaries. Those boundaries map to domain concepts (Order, Customer, Payment, Shipment). Early in a product's life, you don't know which domain concepts will be stable. If you decompose too early and discover the wrong boundaries, you end up with services that need to change in lockstep — the distributed monolith anti-pattern. Build the monolith first; the correct service boundaries emerge from the code under real usage.
|
|
61
|
+
|
|
62
|
+
**Development velocity is the primary constraint.**
|
|
63
|
+
A monolith has one repository, one build, one deploy pipeline, one database, one set of logs. Debugging is `puts` and a stack trace, not distributed tracing across 12 services. Feature development doesn't require coordinating contracts across service owners. For a startup trying to find product-market fit, this operational simplicity is worth far more than theoretical deployment independence.
|
|
64
|
+
|
|
65
|
+
**You need reliable distributed transactions.**
|
|
66
|
+
In a single-process monolith with one relational database, a transaction wrapping multiple table writes is trivially achieved with `BEGIN`/`COMMIT`. In a microservices system, this requires sagas, two-phase commit protocols, or eventual consistency patterns — all of which are significantly harder to implement correctly and reason about.
|
|
67
|
+
|
|
68
|
+
### Real-World Reference Points
|
|
69
|
+
|
|
70
|
+
**Stack Overflow (The New Stack, 2023):**
|
|
71
|
+
Handles 1.3 billion monthly page views across 200+ sites. Infrastructure: 9 on-premise web servers, 4 SQL servers (2 clusters), Redis for caching at 60,000 peak ops/sec. Each web server: 64GB RAM, handles 450 peak req/sec at 12% CPU utilisation. Deliberately chose not to adopt microservices. Their position: "by minimizing the number of external application services, the need to pay 'SOA tax' has been avoided."
|
|
72
|
+
|
|
73
|
+
**Shopify (Shopify Engineering Blog):**
|
|
74
|
+
One of the oldest, largest Rails codebases in existence — 2.8 million lines of code, 500,000+ commits, hundreds of engineers. Ran as a single deployable Rails application through $1B+ GMV. Rather than decomposing to microservices, they built Packwerk (open source) to enforce modular boundaries within the monolith. The result is a modular monolith where components can't reach into each other's internals, giving them microservice-level isolation without the operational overhead. Handles 30TB of data per minute on Black Friday.
|
|
75
|
+
|
|
76
|
+
**Basecamp / DHH ("The Majestic Monolith", 2016):**
|
|
77
|
+
DHH coined "The Majestic Monolith" to describe the intentional choice of a single, integrated Rails application. Basecamp 3 serves the web app, iOS, Android, Windows, and Mac desktop apps, and email, all from one Rails codebase, maintained by approximately 12 programmers. DHH's position: "The only possible way to support multiple platforms with a small team is to explicitly choose and commit to The Majestic Monolith. One generalist can ship an entire feature to everyone on every platform at once."
|
|
78
|
+
|
|
79
|
+
**Amazon Prime Video (2023):**
|
|
80
|
+
The Prime Video quality analysis team had built a distributed serverless architecture for monitoring video streams. It hit a hard scaling wall at 5% of expected load due to data transfer costs between Lambda functions and S3. The team moved all components into a single process (in-process memory transfer instead of S3 round-trips), eliminated the intermediate storage layer, and reduced infrastructure costs by 90% while removing the scaling limit. Note: this was one component of Prime Video, not the whole service — but the lesson stands: distributed is not always better.
|
|
81
|
+
|
|
82
|
+
**StackExchange Network:**
|
|
83
|
+
The entire Q&A network (Stack Overflow, Server Fault, Super User, and 200+ sites) runs from a single .NET monolith. The team demonstrated at QCon New York 2015 that vertical scaling + aggressive caching outperformed what a horizontally distributed system would have cost them to build and operate.
|
|
84
|
+
|
|
85
|
+
---
|
|
86
|
+
|
|
87
|
+
## When NOT to Use It
|
|
88
|
+
|
|
89
|
+
Every architecture has a natural ceiling. The monolith's ceiling is real. Pushing past it causes organisational pain that compounds faster than the accumulated technical debt.
|
|
90
|
+
|
|
91
|
+
### Critical Signals — Time to Evolve
|
|
92
|
+
|
|
93
|
+
**Team scaling pain (30+ developers on a single codebase).**
|
|
94
|
+
When more than ~30 developers commit to the same repository, merge conflicts become a daily drag. Feature branches diverge further before integration. The build time to validate a change grows because the entire codebase must be compiled and tested for every commit. Code ownership becomes ambiguous — multiple teams touch the same files. The result is coordination overhead that defeats the monolith's speed advantage.
|
|
95
|
+
|
|
96
|
+
**Build times exceeding 20–30 minutes.**
|
|
97
|
+
This is the clearest quantitative signal. When the test suite takes 30 minutes to run, developers stop running it locally. The feedback loop breaks. Feature branches stay open longer. Integration failures become more expensive to fix. At this point, the build time is a hard ceiling on deployment frequency, regardless of how well the code is structured.
|
|
98
|
+
|
|
99
|
+
**Deployment coupling: one team's bad deploy takes down everyone.**
|
|
100
|
+
In a monolith, a deploy is all-or-nothing. If Team A ships a memory leak, Team B, C, and D's features all go down on the next deployment. The blast radius of every deploy is the entire product. When the organisation has grown to the point where this coordination tax is daily, and when the cost of a rollback affects multiple teams, independent deployment becomes worth the microservices overhead.
|
|
101
|
+
|
|
102
|
+
**Genuine independent scaling requirements.**
|
|
103
|
+
Video encoding needs 100x compute at peak but only runs for seconds; the billing system needs constant low-compute availability; the recommendation engine needs GPU access. If different components have radically different compute profiles, you're wasting money running them in the same process at the same scale. This is when selective extraction pays off.
|
|
104
|
+
|
|
105
|
+
**Polyglot requirements.**
|
|
106
|
+
Machine learning models in Python, high-throughput APIs in Go, frontend server-side rendering in Node. A monolith is language-locked. If a specific component has a legitimate reason to run in a different language (not fashion — reason), extraction makes sense.
|
|
107
|
+
|
|
108
|
+
**More than ~150 developers, multiple autonomous product teams, 10M+ DAU.**
|
|
109
|
+
Amazon's decomposition (early 2000s) was driven by hundreds of engineers needing to deploy independently, own their services end-to-end, and make technology decisions without coordinating with a central team. The two-pizza team model (8 engineers max per service, full stack ownership) requires microservices to work. This is a valid reason — but it requires all three conditions: large team, genuine team autonomy, and high traffic. Most products never reach this point.
|
|
110
|
+
|
|
111
|
+
### The Most Common Mistake
|
|
112
|
+
|
|
113
|
+
Teams reach for microservices at 5 engineers because they read that Netflix uses them. Netflix has ~2,000 engineers and 200M+ subscribers. The operational overhead of their architecture is spread across a massive engineering organisation. Adopting that architecture at 5 engineers means one person is writing product code and everyone else is managing infrastructure.
|
|
114
|
+
|
|
115
|
+
---
|
|
116
|
+
|
|
117
|
+
## How It Works
|
|
118
|
+
|
|
119
|
+
### Deployment Model
|
|
120
|
+
|
|
121
|
+
A monolith is packaged and deployed as a single artifact:
|
|
122
|
+
- **Ruby/Rails**: A Puma-served Rack application (or Passenger in older setups)
|
|
123
|
+
- **Java/Spring Boot**: A single fat JAR embedding Tomcat or Jetty
|
|
124
|
+
- **Python/Django**: A Gunicorn-served WSGI application
|
|
125
|
+
- **Node/NestJS**: A single Node.js process
|
|
126
|
+
- **PHP/Laravel**: Apache or Nginx + PHP-FPM serving one application root
|
|
127
|
+
- **.NET**: A single IIS application or Kestrel-served .NET process
|
|
128
|
+
|
|
129
|
+
One artifact is built in CI, pushed to a container registry or server, and started. There is no service mesh, no inter-process communication protocol, no API gateway routing between internal services.
|
|
130
|
+
|
|
131
|
+
### Request Handling
|
|
132
|
+
|
|
133
|
+
All code that handles a request lives in the same process. When a web request arrives at the payments controller, it calls the order service, which calls the inventory module, which queries the database — all as in-memory function calls. No network serialisation, no HTTP client, no retry logic, no distributed tracing headers. Latency is nanoseconds-to-microseconds for each call within the process, versus milliseconds across the network.
|
|
134
|
+
|
|
135
|
+
### Database Access
|
|
136
|
+
|
|
137
|
+
Typically one primary relational database (PostgreSQL or MySQL). All modules share access to all tables. This is both a strength (ACID transactions across domain boundaries are trivial) and a risk (module boundaries are enforced only by discipline, not by network topology). Read replicas and connection pooling (PgBouncer, ProxySQL) handle read-heavy load. Sharding by tenant ID (as Shopify does with shop_id on MySQL/Vitess) handles extreme multi-tenant scale.
|
|
138
|
+
|
|
139
|
+
### Session Handling
|
|
140
|
+
|
|
141
|
+
Sessions stored in a shared cache (Redis) or database. All instances of the monolith can serve any request from any user because session state is externalised. This is what enables horizontal scaling: spin up more instances behind a load balancer, all of them connect to the same Redis and database.
|
|
142
|
+
|
|
143
|
+
### Shared Infrastructure
|
|
144
|
+
|
|
145
|
+
- One CI pipeline (one build, one test suite, one deploy step)
|
|
146
|
+
- One application log stream (structured JSON to stdout, aggregated by a log collector)
|
|
147
|
+
- One metrics namespace (one set of dashboards, one alerting configuration)
|
|
148
|
+
- One deployment rollback target
|
|
149
|
+
|
|
150
|
+
Debugging in a monolith is a single stack trace. A 500 error in production shows you exactly which file, line, and function failed. No distributed trace correlation across 12 service boundaries is needed.
|
|
151
|
+
|
|
152
|
+
---
|
|
153
|
+
|
|
154
|
+
## Trade-Offs Matrix
|
|
155
|
+
|
|
156
|
+
| You Get | You Pay |
|
|
157
|
+
|---|---|
|
|
158
|
+
| Simple local development (one `docker compose up`) | Single language/runtime for the entire system |
|
|
159
|
+
| In-process function calls (nanosecond latency) | Can't scale components independently |
|
|
160
|
+
| ACID transactions across domain boundaries | Full redeploy required to ship any change |
|
|
161
|
+
| One build, one deploy pipeline | One team's deploy incident affects all teams |
|
|
162
|
+
| Single unified log stream and metrics | Build/test time grows with codebase size |
|
|
163
|
+
| Easy rollback (redeploy previous artifact) | Risk of "big ball of mud" without enforced module boundaries |
|
|
164
|
+
| No distributed systems problems (split-brain, partial failure, eventual consistency) | Language lock-in — can't use Python for ML in the same process |
|
|
165
|
+
| Easy refactoring (cross-module changes in one commit) | Single point of deployment failure |
|
|
166
|
+
| Lower infrastructure cost (one container vs. dozens) | Database becomes a shared global state risk |
|
|
167
|
+
| Faster onboarding (one codebase to understand) | Memory pressure: all modules in one process |
|
|
168
|
+
|
|
169
|
+
---
|
|
170
|
+
|
|
171
|
+
## Evolution Path
|
|
172
|
+
|
|
173
|
+
The path from monolith to distributed system should be incremental, not a big-bang rewrite. Big-bang rewrites fail — the second system carries the complexity of the first without the battle-hardened knowledge embedded in the original code.
|
|
174
|
+
|
|
175
|
+
### Stage 1: Single-Process Monolith
|
|
176
|
+
Start here. Always. One process, one database, one deploy. Focus on shipping the product. Apply feature-slice folder organisation (not layer-based) from the start so modules are naturally separated. This is the stage where domain boundaries become visible under real usage.
|
|
177
|
+
|
|
178
|
+
### Stage 2: Modular Monolith
|
|
179
|
+
When the codebase grows past ~50,000 LOC and has 10+ developers, introduce explicit module boundaries within the monolith. Modules have defined public interfaces. Other modules cannot reach into private implementation. Dependencies between modules are declared and enforced (Packwerk for Rails, Java modules, .NET namespaces with analyser rules). The deployment unit remains a single process, but the internal structure mirrors what a service decomposition would look like — without the operational overhead. This is where Shopify lives today.
|
|
180
|
+
|
|
181
|
+
### Stage 3: Selective Extraction
|
|
182
|
+
When a specific module has a legitimate, quantifiable reason to be extracted (independent scaling requirement, polyglot language need, team ownership boundary, data isolation requirement), extract it using the strangler fig pattern:
|
|
183
|
+
1. Build an identical external interface for the new service
|
|
184
|
+
2. Deploy a proxy/API gateway that routes a percentage of traffic to the new service
|
|
185
|
+
3. Run the old code path and new code path in parallel and compare results
|
|
186
|
+
4. Shift traffic to the new service incrementally
|
|
187
|
+
5. Remove the old code path from the monolith after validation
|
|
188
|
+
|
|
189
|
+
Extract surgically. Do not extract speculatively. Most modules should remain in the modular monolith indefinitely.
|
|
190
|
+
|
|
191
|
+
### Stage 4: Microservices (Where Appropriate)
|
|
192
|
+
A small number of genuinely independent services alongside a modular monolith that still handles the core product. This is the architecture of most mature products that call themselves "microservices" — they have 3–8 true services extracted for specific reasons, and a monolith (or modular monolith) that does the heavy lifting.
|
|
193
|
+
|
|
194
|
+
### Signals to Evolve (Quantitative Thresholds)
|
|
195
|
+
|
|
196
|
+
| Signal | Threshold | Action |
|
|
197
|
+
|---|---|---|
|
|
198
|
+
| Test suite runtime | > 20 minutes | Introduce module-level test suites; consider extraction |
|
|
199
|
+
| Deploy conflicts | > 2 per week | Introduce module boundaries; evaluate team ownership |
|
|
200
|
+
| Build time | > 30 minutes | Time to move to modular monolith or extract |
|
|
201
|
+
| Team size | > 30 on one codebase | Enforce modules; consider extraction for independent teams |
|
|
202
|
+
| Traffic | > 10M DAU | Evaluate component-level scaling requirements |
|
|
203
|
+
| Deploy frequency | < 1/day due to coordination | Extraction for that team's domain |
|
|
204
|
+
|
|
205
|
+
### Do Not Skip the Modular Monolith Step
|
|
206
|
+
|
|
207
|
+
The most expensive architectural mistake is jumping from a single-process monolith directly to microservices without going through a modular monolith phase. The modular monolith forces you to define stable module boundaries before you incur the operational overhead of distributing them. Teams that skip this step discover their service boundaries are wrong only after they've paid the cost of the network, the service contracts, and the deployment pipelines.
|
|
208
|
+
|
|
209
|
+
---
|
|
210
|
+
|
|
211
|
+
## Failure Modes
|
|
212
|
+
|
|
213
|
+
### Big Ball of Mud
|
|
214
|
+
|
|
215
|
+
The most common monolith failure mode. No internal structure. Every module reaches directly into every other module's database tables. Controller code calls service code calls model code calls other controllers. Circular dependencies everywhere. Changes anywhere break things everywhere. This is not a monolith problem — it is a discipline problem. It happens in microservices too (as a distributed big ball of mud). Prevention: enforce module boundaries from day one, even informally. Use feature-slice folder organisation. Do not allow cross-module database access from the start.
|
|
216
|
+
|
|
217
|
+
**Symptom:** "We can't change anything without breaking something else." **Cause:** No enforced module isolation. **Fix:** Introduce modular monolith tooling (Packwerk, Java modules, namespace rules) to surface and eliminate cross-module dependencies.
|
|
218
|
+
|
|
219
|
+
### Distributed Monolith
|
|
220
|
+
|
|
221
|
+
The worst outcome: a team decomposes the monolith into services but doesn't fix the coupling. Services share a database. Services call each other synchronously in chains 4 deep. A deploy of Service A requires simultaneous deploys of Services B, C, and D. You now have all the complexity of microservices (distributed tracing, network failures, service discovery, API versioning) and all the coupling of a monolith (no independent deployment, no independent scaling). This is not a monolith problem and not a microservices solution — it is the result of extracting services before establishing domain boundaries.
|
|
222
|
+
|
|
223
|
+
**Symptom:** "We deploy all 12 services at once every Friday." **Cause:** Premature extraction without domain boundary analysis. **Fix:** Either re-consolidate into a monolith and re-extract correctly, or systematically remove shared database access and synchronous coupling.
|
|
224
|
+
|
|
225
|
+
### Deployment Bottleneck
|
|
226
|
+
|
|
227
|
+
One team's code is always blocking the deploy train. Their feature is half-done, or their tests are flaky, or their merge conflicts aren't resolved. Every other team waits. This is an organisational signal that teams have grown past what a shared deploy pipeline can accommodate. **Fix:** Move to a modular monolith with module-level CI validation, or extract the offending team's domain into its own service.
|
|
228
|
+
|
|
229
|
+
### Database Contention
|
|
230
|
+
|
|
231
|
+
All modules write to the same database. A background job table scan locks rows that the user-facing API needs to read. A reporting query holds a full-table lock for 30 seconds. This is a monolith performance failure mode that grows worse with scale. **Fix:** Separate read replicas for analytics/reporting, connection pooling, query optimisation. If the problem persists, consider schema-level isolation (each module owns its tables and accesses them only via its own service layer — a prerequisite for eventual extraction).
|
|
232
|
+
|
|
233
|
+
### Context Rot / "God Object" Domain Model
|
|
234
|
+
|
|
235
|
+
A single `User` model with 200 methods, a `Order` model with 150 associations, an `ApplicationHelper` with 400 utility functions. The domain model accumulates all behaviour over time into a small number of central objects. Any change to these objects has unpredictable blast radius. **Fix:** Introduce domain-driven design concepts: bounded contexts, aggregate roots, application services. The fix is structural refactoring, not decomposition.
|
|
236
|
+
|
|
237
|
+
### Real Incident Pattern: The Midnight Deploy
|
|
238
|
+
|
|
239
|
+
A monolith with no feature flags and manual QA deploys at 11pm on a Friday. A new feature has an N+1 query that doesn't manifest in staging but fires on production data. The entire application slows to a halt. There is no way to disable just the new feature without rolling back the entire deploy, which reverts three other teams' work. **Prevention:** Feature flags, automated performance regression testing, canary deployments (route 5% of traffic to new version before full rollout).
|
|
240
|
+
|
|
241
|
+
---
|
|
242
|
+
|
|
243
|
+
## Technology Landscape
|
|
244
|
+
|
|
245
|
+
### Framework Options by Language
|
|
246
|
+
|
|
247
|
+
**Ruby — Ruby on Rails**
|
|
248
|
+
The canonical monolith framework. Convention over configuration. ActiveRecord ORM. Built-in asset pipeline. Hotwire (Turbo + Stimulus) for modern reactive UIs without JavaScript frameworks. Battle-proven at Shopify, GitHub (before their partial extraction), Basecamp, Airbnb (early stage), Gitlab. Packwerk for modular boundary enforcement.
|
|
249
|
+
|
|
250
|
+
**Python — Django**
|
|
251
|
+
"The web framework for perfectionists with deadlines." ORM, admin UI, authentication, migrations included. Used by Instagram (ran as a Django monolith through 400M users before selective extraction), Pinterest (early stage), Disqus. Django apps provide natural module boundaries within the monolith.
|
|
252
|
+
|
|
253
|
+
**PHP — Laravel**
|
|
254
|
+
The dominant PHP framework. Eloquent ORM, Artisan CLI, built-in queue system. Used by Laravel Forge, Laracasts, and a significant proportion of e-commerce and content sites. PHP's shared-nothing architecture (each request a fresh process) makes horizontal scaling straightforward.
|
|
255
|
+
|
|
256
|
+
**Java — Spring Boot**
|
|
257
|
+
The enterprise standard. Embedded Tomcat/Jetty. Dependency injection via Spring container. Strong support for modular monolith patterns via Java modules (JPMS) or Maven/Gradle multi-module projects. Used by Atlassian's Jira/Confluence in early stages, LinkedIn (early), eBay.
|
|
258
|
+
|
|
259
|
+
**Elixir — Phoenix**
|
|
260
|
+
High-performance, fault-tolerant monolith framework. BEAM VM provides process isolation within the monolith — each request runs in its own lightweight process. Built-in Phoenix LiveView for reactive UIs. Designed for multi-core utilisation. 2M connected WebSocket clients from a single server is a documented benchmark.
|
|
261
|
+
|
|
262
|
+
**Node.js — NestJS**
|
|
263
|
+
TypeScript-first, Angular-inspired module system. Dependency injection, decorators, built-in module boundaries. Suitable for teams coming from a TypeScript/Angular background.
|
|
264
|
+
|
|
265
|
+
**.NET — ASP.NET Core**
|
|
266
|
+
Microsoft's modern web framework. Excellent performance (Kestrel server). Strong tooling (Visual Studio, Rider). Used by Stack Overflow (ASP.NET MVC), GitHub Copilot backend components. .NET namespaces + Roslyn analyser rules can enforce module boundaries.
|
|
267
|
+
|
|
268
|
+
**Go — Standard library / Chi / Echo**
|
|
269
|
+
Go is less opinionated about monolith vs. microservices. Single Go binary deployment is extremely clean. Good fit when team is Go-native and wants monolith simplicity with Go performance.
|
|
270
|
+
|
|
271
|
+
### Database
|
|
272
|
+
|
|
273
|
+
The default is a single **PostgreSQL** (or MySQL for legacy/Shopify-style) instance with:
|
|
274
|
+
- Connection pooling: PgBouncer (PostgreSQL), ProxySQL (MySQL)
|
|
275
|
+
- Read replicas: route SELECT queries to replicas, writes to primary
|
|
276
|
+
- Backups: pg_dump or WAL-based continuous archiving to S3
|
|
277
|
+
- Migrations: handled by the framework ORM's migration system (Rails migrations, Alembic, Flyway)
|
|
278
|
+
|
|
279
|
+
For extreme multi-tenant scale, Shopify's model applies: shard by tenant ID across multiple database clusters (shop_id → cluster assignment), so no single database cluster becomes a global bottleneck.
|
|
280
|
+
|
|
281
|
+
### Deployment
|
|
282
|
+
|
|
283
|
+
**Docker (single container):**
|
|
284
|
+
```dockerfile
|
|
285
|
+
FROM ruby:3.3-slim
|
|
286
|
+
WORKDIR /app
|
|
287
|
+
COPY . .
|
|
288
|
+
RUN bundle install --without development test
|
|
289
|
+
EXPOSE 3000
|
|
290
|
+
CMD ["bundle", "exec", "puma", "-C", "config/puma.rb"]
|
|
291
|
+
```
|
|
292
|
+
One image, one container. Deployed to ECS, Kubernetes (single deployment/replicas), or a PaaS.
|
|
293
|
+
|
|
294
|
+
**PaaS (recommended for small teams):**
|
|
295
|
+
- **Heroku**: git push to deploy. Dynos scale horizontally. Managed PostgreSQL.
|
|
296
|
+
- **Railway**: Modern Heroku alternative. Better pricing, built-in databases.
|
|
297
|
+
- **Render**: Similar to Railway. Good free tier for early products.
|
|
298
|
+
- **Fly.io**: Deploy to edge regions. Good for latency-sensitive applications.
|
|
299
|
+
|
|
300
|
+
PaaS eliminates the Kubernetes operational burden entirely, which is appropriate for teams under 10–15 engineers.
|
|
301
|
+
|
|
302
|
+
**Self-hosted (larger teams):**
|
|
303
|
+
EC2 + Auto Scaling Group, or ECS Fargate. Blue/green deployments via CodeDeploy or a deployment tool. Load balancer (ALB) in front with health check endpoint.
|
|
304
|
+
|
|
305
|
+
### Monitoring
|
|
306
|
+
|
|
307
|
+
A monolith is substantially easier to monitor than a distributed system:
|
|
308
|
+
- **Single log stream**: structured JSON to stdout, collected by Datadog/Logstash/CloudWatch Logs. One query finds any error.
|
|
309
|
+
- **Single metrics namespace**: one APM agent (Datadog APM, New Relic, Scout APM). Traces are in-process — no distributed trace correlation.
|
|
310
|
+
- **Error tracking**: Sentry. One project, one DSN, all errors in one place.
|
|
311
|
+
- **Health check**: `GET /health` returns `{"status": "ok", "db": "ok", "redis": "ok"}`. Load balancer kills instances that fail this check.
|
|
312
|
+
|
|
313
|
+
---
|
|
314
|
+
|
|
315
|
+
## Decision Tree
|
|
316
|
+
|
|
317
|
+
Use this tree to determine the correct architecture for a new project or an existing system facing scaling pressure.
|
|
318
|
+
|
|
319
|
+
```
|
|
320
|
+
New product / greenfield project?
|
|
321
|
+
→ Yes → Monolith. No discussion needed.
|
|
322
|
+
→ No (existing system) → see "Existing System" branch below
|
|
323
|
+
|
|
324
|
+
Team size?
|
|
325
|
+
→ < 5 developers → Monolith. Always.
|
|
326
|
+
→ 5–30 developers
|
|
327
|
+
Traffic < 5M DAU?
|
|
328
|
+
→ Yes → Monolith, structured as modules.
|
|
329
|
+
→ No (high traffic) → Monolith + horizontal scaling first.
|
|
330
|
+
Profile before decomposing.
|
|
331
|
+
→ 30–100 developers
|
|
332
|
+
Independent team ownership needed?
|
|
333
|
+
→ No → Modular monolith.
|
|
334
|
+
→ Yes → Modular monolith first, then selective extraction
|
|
335
|
+
for teams that genuinely need independent deploy.
|
|
336
|
+
→ > 100 developers
|
|
337
|
+
Multiple autonomous teams?
|
|
338
|
+
→ Yes, > 10M DAU, multiple autonomous product orgs
|
|
339
|
+
→ Selective microservices alongside modular monolith core.
|
|
340
|
+
→ Not truly autonomous (shared roadmap, shared deploy)
|
|
341
|
+
→ Modular monolith. Microservices will not help.
|
|
342
|
+
|
|
343
|
+
Domain boundaries known and stable?
|
|
344
|
+
→ No (new product, pivoting, < 12 months in production)
|
|
345
|
+
→ Monolith. Extract when boundaries are proven stable.
|
|
346
|
+
→ Yes (2+ years in production, stable domain model)
|
|
347
|
+
→ Safe to consider selective extraction.
|
|
348
|
+
|
|
349
|
+
Build time?
|
|
350
|
+
→ < 10 minutes → Fine. Stay in monolith.
|
|
351
|
+
→ 10–30 minutes → Invest in modular monolith + parallel test execution.
|
|
352
|
+
→ > 30 minutes → Serious signal. Enforce module boundaries.
|
|
353
|
+
Evaluate extraction for highest-change modules.
|
|
354
|
+
|
|
355
|
+
Existing System branch:
|
|
356
|
+
Currently a monolith, team growing:
|
|
357
|
+
→ Apply modular monolith patterns first.
|
|
358
|
+
→ Only extract when a specific team has a specific, quantified
|
|
359
|
+
reason to deploy independently.
|
|
360
|
+
→ Use strangler fig pattern to extract incrementally.
|
|
361
|
+
Currently microservices, experiencing pain:
|
|
362
|
+
→ Identify services that always deploy together → consolidate.
|
|
363
|
+
→ Identify services sharing a database → they are not microservices.
|
|
364
|
+
→ Re-consolidation (as Amazon Prime Video did) is a valid choice.
|
|
365
|
+
```
|
|
366
|
+
|
|
367
|
+
---
|
|
368
|
+
|
|
369
|
+
## Implementation Sketch
|
|
370
|
+
|
|
371
|
+
### Folder Structure: Feature-Slice Organisation (Preferred)
|
|
372
|
+
|
|
373
|
+
Organise by domain/feature, not by technical layer. Layer-based organisation (`models/`, `controllers/`, `services/`) scatters a feature's code across the codebase. Feature-slice organisation keeps all code for a domain concept together.
|
|
374
|
+
|
|
375
|
+
```
|
|
376
|
+
app/
|
|
377
|
+
modules/
|
|
378
|
+
orders/
|
|
379
|
+
controllers/
|
|
380
|
+
orders_controller.rb
|
|
381
|
+
line_items_controller.rb
|
|
382
|
+
models/
|
|
383
|
+
order.rb
|
|
384
|
+
line_item.rb
|
|
385
|
+
services/
|
|
386
|
+
order_placer.rb
|
|
387
|
+
order_canceller.rb
|
|
388
|
+
order_notifier.rb
|
|
389
|
+
queries/
|
|
390
|
+
orders_query.rb
|
|
391
|
+
events/
|
|
392
|
+
order_placed_event.rb
|
|
393
|
+
serializers/
|
|
394
|
+
order_serializer.rb
|
|
395
|
+
payments/
|
|
396
|
+
controllers/
|
|
397
|
+
payments_controller.rb
|
|
398
|
+
models/
|
|
399
|
+
payment.rb
|
|
400
|
+
refund.rb
|
|
401
|
+
services/
|
|
402
|
+
payment_processor.rb
|
|
403
|
+
refund_issuer.rb
|
|
404
|
+
gateways/
|
|
405
|
+
stripe_gateway.rb
|
|
406
|
+
inventory/
|
|
407
|
+
...
|
|
408
|
+
customers/
|
|
409
|
+
...
|
|
410
|
+
notifications/
|
|
411
|
+
...
|
|
412
|
+
shared/
|
|
413
|
+
concerns/
|
|
414
|
+
presenters/
|
|
415
|
+
lib/
|
|
416
|
+
config/
|
|
417
|
+
db/
|
|
418
|
+
migrations/
|
|
419
|
+
schema.rb
|
|
420
|
+
spec/
|
|
421
|
+
modules/
|
|
422
|
+
orders/
|
|
423
|
+
payments/
|
|
424
|
+
inventory/
|
|
425
|
+
```
|
|
426
|
+
|
|
427
|
+
**Rule:** A module may depend on `shared/`. A module must not reach into another module's internals. Cross-module communication goes through a defined public interface (a service object, an event, or a query object in `shared/`).
|
|
428
|
+
|
|
429
|
+
### Module Interface Pattern
|
|
430
|
+
|
|
431
|
+
```ruby
|
|
432
|
+
# Bad: module reaching into another module's internals
|
|
433
|
+
class OrderPlacer
|
|
434
|
+
def call(cart)
|
|
435
|
+
payment = Payment.find(cart.payment_id) # Reaches into payments module
|
|
436
|
+
payment.stripe_charge_id # Accesses internal field
|
|
437
|
+
end
|
|
438
|
+
end
|
|
439
|
+
|
|
440
|
+
# Good: communicate through a defined interface
|
|
441
|
+
class OrderPlacer
|
|
442
|
+
def call(cart)
|
|
443
|
+
result = Payments::PaymentReader.find(cart.payment_id)
|
|
444
|
+
result.confirmation_token # Only accesses public interface
|
|
445
|
+
end
|
|
446
|
+
end
|
|
447
|
+
```
|
|
448
|
+
|
|
449
|
+
### Database Schema Design
|
|
450
|
+
|
|
451
|
+
Name tables with module prefixes to make ownership visible and catch accidental cross-module joins:
|
|
452
|
+
|
|
453
|
+
```sql
|
|
454
|
+
-- Orders module owns these tables
|
|
455
|
+
CREATE TABLE orders_orders (...);
|
|
456
|
+
CREATE TABLE orders_line_items (...);
|
|
457
|
+
|
|
458
|
+
-- Payments module owns these tables
|
|
459
|
+
CREATE TABLE payments_payments (...);
|
|
460
|
+
CREATE TABLE payments_refunds (...);
|
|
461
|
+
|
|
462
|
+
-- Cross-module references use IDs only, never JOINs
|
|
463
|
+
-- orders_orders.payment_id references payments_payments.id
|
|
464
|
+
-- But the orders module never JOINs to payments_payments
|
|
465
|
+
```
|
|
466
|
+
|
|
467
|
+
### CI/CD Pipeline
|
|
468
|
+
|
|
469
|
+
```yaml
|
|
470
|
+
# .github/workflows/ci.yml (GitHub Actions)
|
|
471
|
+
name: CI
|
|
472
|
+
on: [push, pull_request]
|
|
473
|
+
|
|
474
|
+
jobs:
|
|
475
|
+
test:
|
|
476
|
+
runs-on: ubuntu-latest
|
|
477
|
+
services:
|
|
478
|
+
postgres:
|
|
479
|
+
image: postgres:15
|
|
480
|
+
env:
|
|
481
|
+
POSTGRES_PASSWORD: postgres
|
|
482
|
+
options: >-
|
|
483
|
+
--health-cmd pg_isready
|
|
484
|
+
--health-interval 10s
|
|
485
|
+
--health-timeout 5s
|
|
486
|
+
--health-retries 5
|
|
487
|
+
redis:
|
|
488
|
+
image: redis:7
|
|
489
|
+
options: --health-cmd "redis-cli ping" --health-interval 10s
|
|
490
|
+
|
|
491
|
+
steps:
|
|
492
|
+
- uses: actions/checkout@v4
|
|
493
|
+
- uses: ruby/setup-ruby@v1
|
|
494
|
+
with:
|
|
495
|
+
bundler-cache: true
|
|
496
|
+
- run: bundle exec rails db:schema:load RAILS_ENV=test
|
|
497
|
+
- run: bundle exec rspec --format progress
|
|
498
|
+
- run: bundle exec packwerk check # Enforce module boundaries
|
|
499
|
+
|
|
500
|
+
deploy:
|
|
501
|
+
needs: test
|
|
502
|
+
if: github.ref == 'refs/heads/main'
|
|
503
|
+
runs-on: ubuntu-latest
|
|
504
|
+
steps:
|
|
505
|
+
- uses: actions/checkout@v4
|
|
506
|
+
- name: Build Docker image
|
|
507
|
+
run: docker build -t myapp:${{ github.sha }} .
|
|
508
|
+
- name: Push to ECR
|
|
509
|
+
run: |
|
|
510
|
+
aws ecr get-login-password | docker login --username AWS --password-stdin $ECR_REGISTRY
|
|
511
|
+
docker push $ECR_REGISTRY/myapp:${{ github.sha }}
|
|
512
|
+
- name: Deploy to ECS
|
|
513
|
+
run: |
|
|
514
|
+
aws ecs update-service \
|
|
515
|
+
--cluster production \
|
|
516
|
+
--service myapp \
|
|
517
|
+
--force-new-deployment
|
|
518
|
+
```
|
|
519
|
+
|
|
520
|
+
### Docker Deployment (Production-Ready)
|
|
521
|
+
|
|
522
|
+
```dockerfile
|
|
523
|
+
# Multi-stage build for minimal image size
|
|
524
|
+
FROM ruby:3.3-slim AS builder
|
|
525
|
+
RUN apt-get update && apt-get install -y build-essential libpq-dev nodejs
|
|
526
|
+
WORKDIR /app
|
|
527
|
+
COPY Gemfile Gemfile.lock ./
|
|
528
|
+
RUN bundle install --without development test --jobs 4 --retry 3
|
|
529
|
+
COPY . .
|
|
530
|
+
RUN bundle exec rails assets:precompile RAILS_ENV=production SECRET_KEY_BASE=placeholder
|
|
531
|
+
|
|
532
|
+
FROM ruby:3.3-slim AS runtime
|
|
533
|
+
RUN apt-get update && apt-get install -y libpq5 curl && rm -rf /var/lib/apt/lists/*
|
|
534
|
+
WORKDIR /app
|
|
535
|
+
COPY --from=builder /usr/local/bundle /usr/local/bundle
|
|
536
|
+
COPY --from=builder /app /app
|
|
537
|
+
RUN useradd -m -s /bin/bash appuser && chown -R appuser:appuser /app
|
|
538
|
+
USER appuser
|
|
539
|
+
EXPOSE 3000
|
|
540
|
+
HEALTHCHECK --interval=30s --timeout=10s --start-period=30s --retries=3 \
|
|
541
|
+
CMD curl -f http://localhost:3000/health || exit 1
|
|
542
|
+
CMD ["bundle", "exec", "puma", "-C", "config/puma.rb"]
|
|
543
|
+
```
|
|
544
|
+
|
|
545
|
+
### Health Check Endpoint
|
|
546
|
+
|
|
547
|
+
```ruby
|
|
548
|
+
# config/routes.rb
|
|
549
|
+
get '/health', to: 'health#show'
|
|
550
|
+
|
|
551
|
+
# app/controllers/health_controller.rb
|
|
552
|
+
class HealthController < ApplicationController
|
|
553
|
+
skip_before_action :authenticate_user!
|
|
554
|
+
|
|
555
|
+
def show
|
|
556
|
+
checks = {
|
|
557
|
+
status: 'ok',
|
|
558
|
+
database: database_ok?,
|
|
559
|
+
redis: redis_ok?,
|
|
560
|
+
version: ENV['APP_VERSION'] || 'unknown',
|
|
561
|
+
timestamp: Time.current.iso8601
|
|
562
|
+
}
|
|
563
|
+
|
|
564
|
+
status_code = checks.values.all? { |v| v == true || v == 'ok' } ? :ok : :service_unavailable
|
|
565
|
+
render json: checks, status: status_code
|
|
566
|
+
end
|
|
567
|
+
|
|
568
|
+
private
|
|
569
|
+
|
|
570
|
+
def database_ok?
|
|
571
|
+
ActiveRecord::Base.connection.execute('SELECT 1')
|
|
572
|
+
true
|
|
573
|
+
rescue => e
|
|
574
|
+
Rails.logger.error "Health check DB failure: #{e.message}"
|
|
575
|
+
false
|
|
576
|
+
end
|
|
577
|
+
|
|
578
|
+
def redis_ok?
|
|
579
|
+
Redis.current.ping == 'PONG'
|
|
580
|
+
rescue => e
|
|
581
|
+
Rails.logger.error "Health check Redis failure: #{e.message}"
|
|
582
|
+
false
|
|
583
|
+
end
|
|
584
|
+
end
|
|
585
|
+
```
|
|
586
|
+
|
|
587
|
+
---
|
|
588
|
+
|
|
589
|
+
## Cross-References
|
|
590
|
+
|
|
591
|
+
Related expertise modules to read alongside this one:
|
|
592
|
+
|
|
593
|
+
- **`modular-monolith.md`**: The structured evolution of the single-process monolith. Enforced module boundaries within a single deployable unit. Where Shopify lives. Read this when your team grows past ~15 engineers or the codebase exceeds ~100K LOC.
|
|
594
|
+
- **`microservices.md`**: The distributed alternative. Read this when you have quantified, specific reasons to extract. Contains the operational cost inventory (service mesh, distributed tracing, API gateway, inter-service auth, distributed transactions) so you can evaluate whether the benefit justifies the cost.
|
|
595
|
+
- **`monolith-to-microservices.md`**: The migration path. Strangler fig pattern, anti-corruption layers, domain boundary identification, database decomposition strategies. Read this when extraction is imminent.
|
|
596
|
+
- **`twelve-factor-app.md`**: The operational discipline that makes a monolith cloud-native: environment-based config, stateless processes, externalised sessions, structured logging. Apply all 12 factors to a monolith before considering decomposition.
|
|
597
|
+
- **`layered-architecture.md`**: The anti-pattern to avoid within a monolith. Layer-based folder organisation (`controllers/`, `models/`, `services/` at the top level) creates cross-cutting modules that resist extraction and encourage coupling. Feature-slice organisation (this document) is preferred.
|
|
598
|
+
|
|
599
|
+
---
|
|
600
|
+
|
|
601
|
+
## Summary Judgement
|
|
602
|
+
|
|
603
|
+
The monolith is not a legacy pattern. It is the correct default pattern. Distributed systems are appropriate for specific organisations with specific scale and team-size problems that most products never encounter.
|
|
604
|
+
|
|
605
|
+
The question is never "should we use microservices?" The question is "what evidence do we have that the monolith has become a genuine bottleneck?" Until that evidence is concrete and quantified — not theoretical, not aspirational, not because Netflix does it — the monolith (or its evolution, the modular monolith) is the right choice.
|
|
606
|
+
|
|
607
|
+
Build the monolith. Ship the product. Let the domain boundaries emerge. Structure the monolith as modules. Only then, when a specific module has a specific, quantified reason to be independent — extract it.
|
|
608
|
+
|
|
609
|
+
---
|
|
610
|
+
|
|
611
|
+
*Researched: 2026-03-08*
|
|
612
|
+
|
|
613
|
+
*Sources:*
|
|
614
|
+
- *[The Majestic Monolith — DHH / Signal v. Noise](https://signalvnoise.com/svn3/the-majestic-monolith/)*
|
|
615
|
+
- *[Under Deconstruction: The State of Shopify's Monolith — Shopify Engineering](https://shopify.engineering/shopify-monolith)*
|
|
616
|
+
- *[Deconstructing the Monolith — Shopify Engineering](https://shopify.engineering/deconstructing-monolith-designing-software-maximizes-developer-productivity)*
|
|
617
|
+
- *[How Shopify Migrated to a Modular Monolith — InfoQ](https://www.infoq.com/news/2019/07/shopify-modular-monolith/)*
|
|
618
|
+
- *[Stack Overflow Architecture — Dr Milan Milanović](https://newsletter.techworld-with-milan.com/p/stack-overflow-architecture)*
|
|
619
|
+
- *[Scaling Stack Overflow: Keeping it Vertical — QCon New York](https://qconnewyork.com/ny2015/ny2015/presentation/how-vertical-your-monolith-scaling-approach-stack-exchange-and-stackoverflow.html)*
|
|
620
|
+
- *[The macro problem with microservices — Stack Overflow Blog](https://stackoverflow.blog/2020/11/23/the-macro-problem-with-microservices/)*
|
|
621
|
+
- *[Return of the Monolith: Amazon Dumps Microservices for Video Monitoring — The New Stack](https://thenewstack.io/return-of-the-monolith-amazon-dumps-microservices-for-video-monitoring/)*
|
|
622
|
+
- *[Amazon's Two Pizza Teams — AWS Executive Insights](https://aws.amazon.com/executive-insights/content/amazon-two-pizza-team/)*
|
|
623
|
+
- *[Why the Best Startups Still Use Monoliths — ITNEXT](https://itnext.io/why-the-best-startups-still-use-monoliths-fbef26a64193)*
|
|
624
|
+
- *[Monolith vs Microservices in 2025 — foojay.io](https://foojay.io/today/monolith-vs-microservices-2025/)*
|
|
625
|
+
- *[Seven Hard-Earned Lessons Migrating a Monolith to Microservices — InfoQ](https://www.infoq.com/articles/lessons-learned-monolith-microservices/)*
|
|
626
|
+
- *[Strangler Fig Pattern — AWS Prescriptive Guidance](https://docs.aws.amazon.com/prescriptive-guidance/latest/cloud-design-patterns/strangler-fig.html)*
|