@thierrynakoa/fire-flow 12.2.1 → 13.0.1
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/CREDITS.md +25 -0
- package/DOMINION-FLOW-OVERVIEW.md +182 -38
- package/README.md +399 -455
- package/TROUBLESHOOTING.md +264 -264
- package/agents/fire-debugger.md +54 -0
- package/agents/fire-executor.md +1610 -1033
- package/agents/fire-fact-checker.md +1 -1
- package/agents/fire-planner.md +85 -17
- package/agents/fire-project-researcher.md +1 -1
- package/agents/fire-researcher.md +4 -22
- package/agents/{fire-phoenix-analyst.md → fire-resurrection-analyst.md} +394 -394
- package/agents/fire-reviewer.md +552 -499
- package/agents/fire-verifier.md +114 -19
- package/bin/cli.js +18 -101
- package/commands/fire-0-orient.md +2 -2
- package/commands/fire-1a-new.md +50 -15
- package/commands/fire-1c-setup.md +33 -5
- package/commands/fire-1d-discuss.md +87 -1
- package/commands/fire-2-plan.md +556 -527
- package/commands/fire-3-execute.md +2046 -1356
- package/commands/fire-4-verify.md +975 -906
- package/commands/fire-5-handoff.md +46 -5
- package/commands/fire-6-resume.md +2 -31
- package/commands/fire-add-new-skill.md +138 -19
- package/commands/fire-autonomous.md +14 -2
- package/commands/fire-complete-milestone.md +1 -1
- package/commands/fire-cost.md +179 -183
- package/commands/fire-debug.md +1 -6
- package/commands/fire-loop-resume.md +2 -2
- package/commands/fire-loop-stop.md +1 -1
- package/commands/fire-loop.md +2 -15
- package/commands/fire-map-codebase.md +1 -1
- package/commands/fire-migrate-database.md +548 -0
- package/commands/fire-new-milestone.md +1 -1
- package/commands/fire-reflect.md +1 -2
- package/commands/fire-research.md +142 -21
- package/commands/{fire-phoenix.md → fire-resurrect.md} +859 -603
- package/commands/fire-scaffold.md +297 -0
- package/commands/fire-search.md +1 -2
- package/commands/fire-security-scan.md +483 -484
- package/commands/fire-setup.md +359 -0
- package/commands/fire-skill.md +770 -0
- package/commands/fire-skills-diff.md +506 -506
- package/commands/fire-skills-history.md +388 -388
- package/commands/fire-skills-rollback.md +7 -7
- package/commands/fire-skills-sync.md +470 -470
- package/commands/fire-test.md +5 -5
- package/commands/fire-todos.md +1 -1
- package/commands/fire-update.md +5 -5
- package/commands/fire-validate-skills.md +282 -0
- package/commands/fire-vuln-scan.md +492 -493
- package/hooks/run-hook.sh +8 -8
- package/hooks/run-session-end.sh +7 -7
- package/hooks/session-end.sh +90 -90
- package/hooks/session-start.sh +1 -1
- package/package.json +4 -24
- package/plugin.json +7 -7
- package/references/autonomy-levels.md +235 -0
- package/references/behavioral-directives.md +95 -3
- package/references/blocker-tracking.md +1 -1
- package/references/circuit-breaker.md +93 -2
- package/references/context-engineering.md +227 -9
- package/references/honesty-protocols.md +70 -1
- package/references/issue-to-pr-pipeline.md +149 -150
- package/references/metrics-and-trends.md +1 -2
- package/references/research-improvements.md +4 -108
- package/references/sdlc-mapping.md +73 -0
- package/references/state-machine.md +151 -0
- package/skills-library/AVAILABLE_TOOLS_REFERENCE.md +333 -0
- package/skills-library/SKILLS-INDEX.md +57 -558
- package/skills-library/SKILLS_LIBRARY_INDEX.md +532 -0
- package/skills-library/_general/api-patterns/api-field-name-mismatch.md +107 -0
- package/skills-library/_general/api-patterns/streaming-command-timeout.md +122 -0
- package/skills-library/_general/api-patterns/streaming-proxy-cors-bypass.md +102 -0
- package/skills-library/_general/automation/settings-gui-generator.md +172 -0
- package/skills-library/_general/database-solutions/data-type-mapping-reference.md +181 -0
- package/skills-library/_general/database-solutions/mysql-limit-offset-string-coercion.md +102 -0
- package/skills-library/_general/database-solutions/mysql-to-pg-migration.md +195 -0
- package/skills-library/_general/database-solutions/orm-schema-portability.md +193 -0
- package/skills-library/_general/database-solutions/persistent-analysis-storage.md +207 -0
- package/skills-library/_general/database-solutions/pg-to-mysql-schema-migration-methodology.md +190 -0
- package/skills-library/_general/database-solutions/sql-dialect-compatibility-matrix.md +306 -0
- package/skills-library/_general/database-solutions/sqlite-to-pg-migration.md +219 -0
- package/skills-library/_general/frontend/canvas-bubble-animation-grouping.md +270 -0
- package/skills-library/_general/frontend/color-token-migration.md +112 -0
- package/skills-library/_general/frontend/framer-motion-layoutid-grouping.md +150 -0
- package/skills-library/_general/frontend/pyqt6-settings-dialog.md +191 -0
- package/skills-library/_general/frontend/react-flow-animated-layout-switching.md +101 -0
- package/skills-library/_general/frontend/react-hooks-order-debugging.md +141 -0
- package/skills-library/_general/frontend/redux-localstorage-auth-desync.md +126 -0
- package/skills-library/_general/frontend/safari-csp-theme-color-debugging.md +124 -0
- package/skills-library/_general/frontend/safari-sw-cache-poisoning.md +138 -0
- package/skills-library/_general/frontend/svg-sparkline-no-charting-library.md +131 -0
- package/skills-library/_general/growth-marketing/oss-daily-growth-intelligence.md +224 -0
- package/skills-library/_general/integrations/claude-code-local-mcp-integration.md +250 -0
- package/skills-library/_general/integrations/mcp-composite-tool-orchestration.md +200 -0
- package/skills-library/_general/methodology/AGENT_SDK_STANDALONE_TOOLING.md +181 -0
- package/skills-library/_general/methodology/AGENT_TEAMS_GUIDE.md +169 -0
- package/skills-library/_general/methodology/ALAS_STATEFUL_EXECUTION.md +207 -0
- package/skills-library/_general/methodology/AUTO_REVIEWER_SUBAGENT.md +211 -0
- package/skills-library/_general/methodology/CONSISTENCY_CHECK_AMBIGUITY_GATE.md +96 -0
- package/skills-library/_general/methodology/DEAD_ENDS_SHELF.md +4 -4
- package/skills-library/_general/methodology/DISTILL_NOT_DUMP.md +108 -0
- package/skills-library/_general/methodology/EXECUTION_PROGRESS_MONITOR.md +157 -0
- package/skills-library/_general/methodology/HIERARCHICAL_REVIEW_MARS.md +122 -0
- package/skills-library/_general/methodology/MCP_INTER_AGENT_BRIDGE.md +207 -0
- package/skills-library/_general/methodology/MERMAID_WIZARD_DIAGRAMS.md +77 -0
- package/skills-library/_general/methodology/MISSING_DIMENSION_DETECTOR.md +89 -0
- package/skills-library/_general/methodology/MULTI_AGENT_COORDINATION.md +397 -0
- package/skills-library/_general/methodology/OBSERVATION_MASKING.md +100 -0
- package/skills-library/_general/methodology/PHOENIX_REBUILD_METHODOLOGY.md +82 -11
- package/skills-library/_general/methodology/REVIEW_BACKTRACK_PANEL.md +140 -0
- package/skills-library/_general/methodology/REVIEW_FIX_LOOP.md +117 -0
- package/skills-library/_general/methodology/VOTING_VERDICT_ARBITRATION.md +155 -0
- package/skills-library/_general/methodology/ZERO_FRICTION_CLI_SETUP.md +2 -2
- package/skills-library/_general/methodology/dead-code-activation.md +123 -0
- package/skills-library/_general/methodology/debug-swarm-researcher-escape-hatch.md +240 -240
- package/skills-library/_general/methodology/shell-autonomous-loop-fixplan.md +1 -1
- package/skills-library/_general/patterns-standards/GOF_DESIGN_PATTERNS_FOR_AI_AGENTS.md +5 -5
- package/skills-library/_general/patterns-standards/cascading-failure-diagnosis.md +119 -0
- package/skills-library/_general/patterns-standards/domain-specific-layout-algorithms.md +209 -0
- package/skills-library/_general/patterns-standards/python-desktop-app-architecture.md +399 -0
- package/skills-library/_general/patterns-standards/realtime-monitoring-dashboard.md +457 -0
- package/skills-library/_general/patterns-standards/togglable-processing-pipeline.md +169 -0
- package/skills-library/_general/performance/liveclock-extraction.md +112 -0
- package/skills-library/_general/performance/ref-based-canvas-animation.md +117 -0
- package/skills-library/_general/performance/use-visible-interval.md +131 -0
- package/skills-library/_general/testing/playwright-firefox-withcredentials-auth-issue.md +104 -0
- package/skills-library/_quarantine/README.md +30 -0
- package/skills-library/api-patterns/BROADCAST_SCHEDULER_SHARED_EXECUTE_FUNCTION.md +150 -0
- package/skills-library/api-patterns/ERROR_RESPONSE_STANDARDS.md +145 -0
- package/skills-library/api-patterns/EXPRESS_ROUTE_ORDERING_MIDDLEWARE_INTERCEPTION.md +326 -0
- package/skills-library/api-patterns/PAGINATION_PATTERNS.md +137 -0
- package/skills-library/api-patterns/PODCAST_PROGRESS_TRACKING_THREE_ROOT_CAUSES.md +277 -0
- package/skills-library/api-patterns/RATE_LIMITING_TOGGLE.md +155 -0
- package/skills-library/api-patterns/graphql-content-queries.md +708 -0
- package/skills-library/appointment-scheduler-design.md +423 -0
- package/skills-library/automation/AUTO_POPULATE_COMPLETE_GUIDE.md +631 -0
- package/skills-library/automation/CC_WORKFLOW_STUDIO.md +83 -0
- package/skills-library/automation/CLAUDE_CODE_SWARM_MODE.md +95 -0
- package/skills-library/automation/DAEMON_TRIGGER_FILE_IPC.md +195 -0
- package/skills-library/automation/scheduled-content-publishing.md +608 -0
- package/skills-library/awesome-workflows/Blogging-Platform-Instructions/view_commands.md +25 -0
- package/skills-library/awesome-workflows/CREDENTIAL-SECURITY-WORKFLOW.md +109 -0
- package/skills-library/awesome-workflows/DEBUGGING-WORKFLOW.md +124 -0
- package/skills-library/awesome-workflows/Design-Review-Workflow/README.md +31 -0
- package/skills-library/awesome-workflows/Design-Review-Workflow/design-principles-example.md +129 -0
- package/skills-library/awesome-workflows/Design-Review-Workflow/design-review-agent.md +107 -0
- package/skills-library/awesome-workflows/Design-Review-Workflow/design-review-claude-md-snippet.md +24 -0
- package/skills-library/awesome-workflows/Design-Review-Workflow/design-review-slash-command.md +38 -0
- package/skills-library/awesome-workflows/PARALLEL-RESEARCH-WORKFLOW.md +89 -0
- package/skills-library/awesome-workflows/PHASE-EXECUTION-WORKFLOW.md +97 -0
- package/skills-library/awesome-workflows/SESSION-HANDOFF-WORKFLOW.md +116 -0
- package/skills-library/cms-patterns/content-branch-preview.md +515 -0
- package/skills-library/cms-patterns/inline-visual-editing.md +666 -0
- package/skills-library/cms-patterns/mdx-component-content.md +649 -0
- package/skills-library/cms-patterns/media-manager-abstraction.md +827 -0
- package/skills-library/cms-patterns/schema-driven-form-generator.md +838 -0
- package/skills-library/complexity-metrics/complexity-divider.md +707 -0
- package/skills-library/complexity-metrics/work-with-complexity.md +193 -0
- package/skills-library/creative-multimedia/animation-stack-guide.md +577 -0
- package/skills-library/creative-multimedia/audio-enhancement-pipeline.md +625 -0
- package/skills-library/creative-multimedia/content-repurposing-pipeline.md +1146 -0
- package/skills-library/creative-multimedia/data-visualization-generator.md +862 -0
- package/skills-library/creative-multimedia/doc-to-podcast-pipeline.md +2184 -0
- package/skills-library/creative-multimedia/ffmpeg-command-generator.md +405 -0
- package/skills-library/creative-multimedia/image-optimization-pipeline.md +605 -0
- package/skills-library/creative-multimedia/multi-format-content-generator.md +1759 -0
- package/skills-library/creative-multimedia/og-image-generator.md +635 -0
- package/skills-library/creative-multimedia/podcast-audio-composition.md +1355 -0
- package/skills-library/creative-multimedia/podcast-quality-evaluation.md +1452 -0
- package/skills-library/creative-multimedia/podcast-script-generation.md +1841 -0
- package/skills-library/creative-multimedia/svg-generation.md +750 -0
- package/skills-library/creative-multimedia/text-to-speech-provider-selector.md +1414 -0
- package/skills-library/creative-multimedia/transcription-pipeline-selector.md +677 -0
- package/skills-library/creative-multimedia/video-streaming-setup.md +559 -0
- package/skills-library/database-solutions/AI_RESPONSE_DATABASE_CACHING.md +520 -0
- package/skills-library/database-solutions/CONDITIONAL_SQL_MIGRATION_PATTERN.md +119 -0
- package/skills-library/database-solutions/DATABASE_COLUMN_NAME_MISMATCH.md +393 -0
- package/skills-library/database-solutions/DATABASE_SCHEMA.md +394 -0
- package/skills-library/database-solutions/DATABASE_SCHEMA_VERIFICATION_GUIDE.md +348 -0
- package/skills-library/database-solutions/DATABASE_STRATEGY.md +71 -0
- package/skills-library/database-solutions/ES_MODULE_SEED_SCRIPT_PATTERN.md +52 -0
- package/skills-library/database-solutions/MIGRATION_GUIDE.md +3 -0
- package/skills-library/database-solutions/PLPGSQL_VARIABLE_CONFLICT_FIX.md +208 -0
- package/skills-library/database-solutions/POSTGRESQL_JSONB_DOUBLE_STRINGIFY_FIX.md +245 -0
- package/skills-library/database-solutions/POSTGRESQL_LICENSE_TABLE_DESIGN.md +393 -0
- package/skills-library/database-solutions/POSTGRESQL_UUID_DOCUMENT_RAG_DUAL_SCOPE.md +732 -0
- package/skills-library/database-solutions/POSTGRES_SQL_TEMPLATE_BINDING_ERROR.md +240 -0
- package/skills-library/database-solutions/PRISMA_DB_PUSH_DATA_LOSS_PREVENTION.md +141 -0
- package/skills-library/database-solutions/PRODUCTION_QUERY_OPTIMIZATION_RESTART_FIX.md +389 -0
- package/skills-library/database-solutions/RLS_SECURITY_GUIDE.md +107 -0
- package/skills-library/database-solutions/SCHEMA_ENHANCEMENTS_GUIDE.md +373 -0
- package/skills-library/database-solutions/SCHEMA_MIGRATION_GUIDE.md +368 -0
- package/skills-library/database-solutions/SCHEMA_VERIFICATION_QUICK_REFERENCE.md +104 -0
- package/skills-library/database-solutions/ai-erd-generator.md +1213 -0
- package/skills-library/database-solutions/content-publishing-states.md +631 -0
- package/skills-library/database-solutions/database-schema-designer.md +522 -0
- package/skills-library/database-solutions/er-diagram-components.md +569 -0
- package/skills-library/database-solutions/er-to-ddl-mapping.md +1405 -0
- package/skills-library/database-solutions/erd-creator-textbook-research.md +433 -0
- package/skills-library/database-solutions/erd-react-flow-architecture.md +1965 -0
- package/skills-library/database-solutions/mariadb-aggregate-function-replacement.md +145 -0
- package/skills-library/database-solutions/normalization-validator.md +778 -0
- package/skills-library/database-solutions/postgres-full-text-search-content.md +494 -0
- package/skills-library/database-solutions/postgresql-to-mysql-runtime-translation.md +286 -0
- package/skills-library/database-solutions/regex-alternation-ordering-sql-types.md +92 -0
- package/skills-library/database-solutions/reserved-word-context-aware-quoting.md +142 -0
- package/skills-library/database-solutions/sql-ddl-generator.md +756 -0
- package/skills-library/database-solutions/supabase-connection-pooler-fix.md +102 -0
- package/skills-library/deployment-security/CPANEL_NODE_DEPLOYMENT.md +166 -0
- package/skills-library/deployment-security/DEPLOYMENT.md +275 -0
- package/skills-library/deployment-security/DEPLOYMENT_CHECKLIST.md +363 -0
- package/skills-library/deployment-security/DEPLOYMENT_PLAN.md +669 -0
- package/skills-library/deployment-security/KNEX_DATABASE_ABSTRACTION.md +444 -0
- package/skills-library/deployment-security/LICENSE_KEY_SYSTEM.md +206 -0
- package/skills-library/deployment-security/NODE18_DEPENDENCY_COMPATIBILITY.md +284 -0
- package/skills-library/deployment-security/PHP_INSTALLER_WIZARD_GUIDE.md +315 -0
- package/skills-library/deployment-security/PM2_ENVIRONMENT_VARIABLE_CACHING.md +256 -0
- package/skills-library/deployment-security/PM2_MEMORY_EXHAUSTION_FIX.md +370 -0
- package/skills-library/deployment-security/PRODUCTION_DEPLOYMENT_GUIDE.md +592 -0
- package/skills-library/deployment-security/PRODUCTION_HARDENING_DOCUMENTATION.md +307 -0
- package/skills-library/deployment-security/PRODUCTION_RECOVERY_CHERRY_PICK_PATTERN.md +202 -0
- package/skills-library/deployment-security/PYINSTALLER_CUDA_WHISPER_BUNDLING.md +236 -0
- package/skills-library/deployment-security/SECURITY.md +41 -0
- package/skills-library/deployment-security/SMTP_SSL_HOSTNAME_MISMATCH_SHARED_HOSTING.md +220 -0
- package/skills-library/deployment-security/SPA_SEO_OPTIMIZATION_CPANEL.md +200 -0
- package/skills-library/deployment-security/SUPABASE_EDGE_FUNCTIONS.md +338 -0
- package/skills-library/deployment-security/VERCEL_GITHUB_DEPLOYMENT_GUIDE.md +858 -0
- package/skills-library/deployment-security/VPS_DEPLOYMENT_READINESS.md +356 -0
- package/skills-library/deployment-security/deployment-changes-not-applying.md +241 -0
- package/skills-library/deployment-security/env-file-management-production-local.md +203 -0
- package/skills-library/deployment-security/express-secure-file-downloads.md +413 -0
- package/skills-library/deployment-security/react-production-deployment-desktop-guide.md +2011 -0
- package/skills-library/deployment-security/self-hosted-supabase-coolify-guide.md +1684 -0
- package/skills-library/deployment-security/unique-features-ai-strategy-plaid-security.md +1613 -0
- package/skills-library/deployment-security/vps-deployment.md +135 -0
- package/skills-library/document-processing/WORD_EXPORT_MARKDOWN_FORMATTING.md +482 -0
- package/skills-library/document-processing/document-ai-landingai-integration.md +677 -0
- package/skills-library/document-processing/express-secure-file-downloads-mern.md +413 -0
- package/skills-library/document-processing/express-secure-file-downloads.md +413 -0
- package/skills-library/document-processing/md-to-word-converter.md +318 -0
- package/skills-library/document-processing/pdf-forms-integration/README.md +101 -0
- package/skills-library/document-processing/pdf-forms-integration/SKILL.md +662 -0
- package/skills-library/ecommerce/ADMIN_PRODUCTS_GUIDE.md +428 -0
- package/skills-library/ecommerce/ECOMMERCE_API_REFERENCE.md +776 -0
- package/skills-library/ecommerce/ECOMMERCE_COMPLETION_SUMMARY.md +673 -0
- package/skills-library/ecommerce/ECOMMERCE_IMPLEMENTATION_GUIDE.md +729 -0
- package/skills-library/ecommerce/ECOMMERCE_QUICK_REFERENCE.md +521 -0
- package/skills-library/ecommerce/ECOMMERCE_TESTING_CHECKLIST.md +565 -0
- package/skills-library/ecommerce/ECOMMERCE_WORKFLOW_GUIDE.md +1059 -0
- package/skills-library/ecommerce/PRODUCT_CREATION_EXPANDED.md +522 -0
- package/skills-library/ecommerce/agentic-commerce-protocol.md +203 -0
- package/skills-library/ecommerce/cart-abandonment-recovery.md +236 -0
- package/skills-library/ecommerce/cart-architecture-patterns.md +300 -0
- package/skills-library/ecommerce/cart-item-count-indicator.md +264 -0
- package/skills-library/ecommerce/checkout-ux-conversion.md +227 -0
- package/skills-library/ecommerce/composable-commerce-selection.md +166 -0
- package/skills-library/ecommerce/ecommerce-analytics-patterns.md +167 -0
- package/skills-library/ecommerce/fraud-detection-patterns.md +179 -0
- package/skills-library/ecommerce/inventory-stock-management.md +270 -0
- package/skills-library/ecommerce/order-saga-state-machine.md +336 -0
- package/skills-library/ecommerce/payment-provider-abstraction.md +245 -0
- package/skills-library/ecommerce/pci-compliance-checklist.md +192 -0
- package/skills-library/ecommerce/refund-chargeback-handling.md +177 -0
- package/skills-library/ecommerce/shipping-carrier-integration.md +218 -0
- package/skills-library/ecommerce/webhook-idempotency-patterns.md +253 -0
- package/skills-library/excalidraw-diagrams/.github/workflows/ci.yml +558 -0
- package/skills-library/excalidraw-diagrams/.github/workflows/prompt-gallery.yml +448 -0
- package/skills-library/excalidraw-diagrams/.github/workflows/release.yml +42 -0
- package/skills-library/excalidraw-diagrams/.github/workflows/test-reusable-ci.yml +25 -0
- package/skills-library/excalidraw-diagrams/CLAUDE.md +57 -0
- package/skills-library/excalidraw-diagrams/LICENSE +21 -0
- package/skills-library/excalidraw-diagrams/README.md +178 -0
- package/skills-library/excalidraw-diagrams/SKILL.md +715 -0
- package/skills-library/form-solutions/BUTTON_TYPE_FORM_SUBMISSION.md +336 -0
- package/skills-library/form-solutions/FILLABLE_PDF_IMPLEMENTATION.md +226 -0
- package/skills-library/form-solutions/SURVEYJS_QUESTIONNAIRE_SYSTEM.md +367 -0
- package/skills-library/form-solutions/tiptap-minimal-setup.md +690 -0
- package/skills-library/frontend/scholarly-classification-bubble-map.md +149 -0
- package/skills-library/infrastructure/ci-cd-pipeline-builder.md +517 -0
- package/skills-library/infrastructure/observability-designer.md +264 -0
- package/skills-library/infrastructure/performance-profiler.md +621 -0
- package/skills-library/installer-wizard-patterns.md +249 -0
- package/skills-library/integrations/CLAUDE_CODE_TOKEN_ANALYTICS.md +160 -0
- package/skills-library/integrations/CONFIGURABLE_AI_PROVIDER_SELECTION.md +728 -0
- package/skills-library/integrations/SOCKET_IO_BROADCAST_ALL_VS_ROOM.md +141 -0
- package/skills-library/integrations/VIRTUAL_MEETINGS_IMPLEMENTATION.md +374 -0
- package/skills-library/integrations/WORDPRESS_LEARNDASH_DATA_RECOVERY.md +53 -0
- package/skills-library/integrations/YOUTUBE_API_SETUP.md +141 -0
- package/skills-library/integrations/YOUTUBE_BOOKMARKING_EXPLANATION.md +252 -0
- package/skills-library/integrations/YOUTUBE_BOOKMARKING_SOLUTION.md +268 -0
- package/skills-library/integrations/YOUTUBE_OAUTH_SETUP_GUIDE.md +200 -0
- package/skills-library/integrations/YOUTUBE_VIDEO_FIX_COMPLETE.md +192 -0
- package/skills-library/integrations/ai-ml/GEMINI_AI_RAG_PIPELINE_COMPLETE_GUIDE.md +195 -0
- package/skills-library/integrations/ai-ml/GEMINI_IMAGE_GENERATION_SETUP.md +64 -0
- package/skills-library/integrations/cloudflare/cloudflare-turnstile-debugging.md +202 -0
- package/skills-library/integrations/cloudflare/cloudflare-turnstile-implementation.md +476 -0
- package/skills-library/integrations/cloudflare-turnstile-debugging.md +202 -0
- package/skills-library/integrations/cloudflare-turnstile-implementation.md +476 -0
- package/skills-library/integrations/ghost-creator-monetization-pattern.md +454 -0
- package/skills-library/integrations/headless-cms-architecture.md +484 -0
- package/skills-library/integrations/headless-cms-stack-selection.md +183 -0
- package/skills-library/integrations/payload-cms-patterns.md +674 -0
- package/skills-library/integrations/realtimestt-openwakeword-cuda-windows.md +229 -0
- package/skills-library/integrations/rss-podcast-integration.md +300 -0
- package/skills-library/integrations/wordpress/WORDPRESS_LEARNDASH_DATA_RECOVERY.md +53 -0
- package/skills-library/integrations/youtube/YOUTUBE_API_SETUP.md +141 -0
- package/skills-library/integrations/youtube/YOUTUBE_BOOKMARKING_EXPLANATION.md +252 -0
- package/skills-library/integrations/youtube/YOUTUBE_BOOKMARKING_SOLUTION.md +268 -0
- package/skills-library/integrations/youtube/YOUTUBE_OAUTH_SETUP_GUIDE.md +200 -0
- package/skills-library/integrations/youtube/YOUTUBE_VIDEO_FIX_COMPLETE.md +192 -0
- package/skills-library/marketing/campaign-analytics.md +97 -0
- package/skills-library/marketing/content-creator.md +105 -0
- package/skills-library/marketing/marketing-strategy-pmm.md +94 -0
- package/skills-library/marketing/social-media-analyzer.md +81 -0
- package/skills-library/methodology/ADVANCED_ORCHESTRATION_PATTERNS.md +401 -0
- package/skills-library/methodology/AGENT_SELF_IMPROVEMENT_LOOP.md +179 -0
- package/skills-library/methodology/BREATH_BASED_PARALLEL_EXECUTION.md +1 -1
- package/skills-library/methodology/CLEANSING_CYCLE.md +358 -0
- package/skills-library/methodology/CONFIDENCE_ANNOTATION_PATTERN.md +143 -0
- package/skills-library/methodology/CRITICAL_PATTERNS_DOCUMENTATION_COMPLETE.md +204 -0
- package/skills-library/methodology/DELIVERABLES_SUMMARY.md +341 -0
- package/skills-library/methodology/DIFFICULTY_AWARE_AGENT_ROUTING.md +252 -0
- package/skills-library/methodology/EVOLUTIONARY_SKILL_SYNTHESIS.md +219 -0
- package/skills-library/methodology/GLOMERULUS_DECISION_GATE.md +223 -0
- package/skills-library/methodology/HIBERNATION_SYSTEM.md +231 -0
- package/skills-library/methodology/INSTRUMENTATION_OVER_RESTRICTION.md +192 -0
- package/skills-library/methodology/MASTER_COMPLETION_SUMMARY.md +444 -0
- package/skills-library/methodology/MASTER_SESSION_COMPLETION.md +743 -0
- package/skills-library/methodology/MERN_QUICK_REFERENCE.md +358 -0
- package/skills-library/methodology/ORGAN_AGENT_MAPPING.md +177 -0
- package/skills-library/methodology/PARALLEL_WAVE_BASED_REFACTORING.md +440 -0
- package/skills-library/methodology/QUICK_REFERENCE.md +358 -0
- package/skills-library/methodology/SDFT_ONPOLICY_SELF_DISTILLATION.md +186 -0
- package/skills-library/methodology/SELF_QUESTIONING_TASK_GENERATION.md +270 -0
- package/skills-library/methodology/SESSION_COMPLETION_SUMMARY.md +304 -0
- package/skills-library/methodology/SESSION_SUMMARY.md +432 -0
- package/skills-library/methodology/WARRIOR_WORKFLOW_DEBUGGING_PROTOCOL.md +252 -0
- package/skills-library/methodology/tech-debt-tracker.md +570 -0
- package/skills-library/parallel-debug/SKILL.md +60 -0
- package/skills-library/patterns-standards/API_PATTERN_FIX_SUMMARY.md +236 -0
- package/skills-library/patterns-standards/BATCH_OPERATIONS_WITH_PROGRESS_MODAL.md +362 -0
- package/skills-library/patterns-standards/CRITICAL_CODING_PATTERNS.md +639 -0
- package/skills-library/patterns-standards/DARK_MODE_MODAL_VISIBILITY.md +258 -0
- package/skills-library/patterns-standards/ERROR_RESILIENCE_IMPLEMENTATION.md +375 -0
- package/skills-library/patterns-standards/ES_MODULE_IMPORT_HOISTING_DOTENV.md +298 -0
- package/skills-library/patterns-standards/NESTED_BACKDROP_FILTER_CSS_ARTIFACT_FIX.md +76 -0
- package/skills-library/patterns-standards/ORDERED_DETECTOR_PIPELINE_GRACEFUL_FALLBACK.md +333 -0
- package/skills-library/patterns-standards/PHASE_IMPORT_ERROR_DEBUGGING.md +271 -0
- package/skills-library/patterns-standards/PYNPUT_GLOBAL_HOTKEY_VK_MATCHING.md +252 -0
- package/skills-library/patterns-standards/REACT_USEEFFECT_CASCADE_RESET_FIX.md +132 -0
- package/skills-library/patterns-standards/SUBMENU_HOVER_DROPDOWN_PATTERN.md +225 -0
- package/skills-library/patterns-standards/TAILWIND_TEXT_VISIBILITY_OVERRIDE.md +322 -0
- package/skills-library/patterns-standards/THEME_AWARE_CSS_VARIABLES_PATTERN.md +209 -0
- package/skills-library/patterns-standards/THEME_USER_OBJECT_PROPERTY_NAMING.md +194 -0
- package/skills-library/patterns-standards/TOOLTIP_BLOCKING_CLICKS_FIX.md +267 -0
- package/skills-library/patterns-standards/claude-code-plugin-structure.md +235 -0
- package/skills-library/patterns-standards/react-i18next-setup.md +429 -0
- package/skills-library/patterns-standards/thesys-c1-generative-ui-integration.md +967 -0
- package/skills-library/plugin-development/CLAUDE_CODE_COMMAND_REGISTRATION_SILENT_FAILURE.md +315 -0
- package/skills-library/plugin-development/plugin-command-namespace-vs-global.md +390 -0
- package/skills-library/plugin-development/plugin-doc-auto-generation.md +172 -0
- package/skills-library/security/GITHUB_REPO_SECURITY_AUDIT.md +115 -0
- package/skills-library/security/admin-deletion-safety.md +396 -0
- package/skills-library/security/application-vuln-patterns.md +477 -0
- package/skills-library/security/env-secrets-manager.md +686 -0
- package/skills-library/security/secure-ai-application-templates.md +347 -0
- package/skills-library/security/sql-injection-prevention-postgresjs.md +151 -0
- package/skills-library/supabase-connection-pooler-fix.md +102 -0
- package/skills-library/system-context/POWERSHELL_BASH_INTEROP.md +82 -0
- package/skills-library/system-context/SERVICE_LIFECYCLE_MANAGEMENT.md +119 -0
- package/skills-library/system-context/SKILL.md +40 -0
- package/skills-library/system-context/WINDOWS_DEV_ENVIRONMENT.md +73 -0
- package/skills-library/testing/E2E_PLAYWRIGHT_PATTERNS.md +99 -0
- package/skills-library/testing/INTEGRATION_TEST_STRATEGY.md +82 -0
- package/skills-library/testing/RED_GREEN_BUGFIX_GATE.md +203 -0
- package/skills-library/testing/TEST_DATA_MANAGEMENT.md +69 -0
- package/skills-library/testing/VITEST_UNIT_TEST_PATTERNS.md +75 -0
- package/skills-library/testing/playwright-api-security-tests.md +202 -0
- package/skills-library/toolbox/SKILL.md +84 -0
- package/skills-library/toolbox/code-graph-and-web-scraping-mcps.md +237 -0
- package/skills-library/ui-ux-pro-max/ACCESSIBILITY_ESSENTIALS.md +115 -0
- package/skills-library/ui-ux-pro-max/DESIGN_SYSTEM_SCAFFOLDING.md +133 -0
- package/skills-library/ui-ux-pro-max/RESPONSIVE_LAYOUT_PATTERNS.md +119 -0
- package/skills-library/ui-ux-pro-max/SKILL.md +386 -0
- package/skills-library/ui-ux-pro-max/data/charts.csv +26 -0
- package/skills-library/ui-ux-pro-max/data/colors.csv +97 -0
- package/skills-library/ui-ux-pro-max/data/icons.csv +101 -0
- package/skills-library/ui-ux-pro-max/data/landing.csv +31 -0
- package/skills-library/ui-ux-pro-max/data/products.csv +97 -0
- package/skills-library/ui-ux-pro-max/data/react-performance.csv +45 -0
- package/skills-library/ui-ux-pro-max/data/stacks/astro.csv +54 -0
- package/skills-library/ui-ux-pro-max/data/stacks/flutter.csv +53 -0
- package/skills-library/ui-ux-pro-max/data/stacks/html-tailwind.csv +56 -0
- package/skills-library/ui-ux-pro-max/data/stacks/jetpack-compose.csv +53 -0
- package/skills-library/ui-ux-pro-max/data/stacks/nextjs.csv +53 -0
- package/skills-library/ui-ux-pro-max/data/stacks/nuxt-ui.csv +51 -0
- package/skills-library/ui-ux-pro-max/data/stacks/nuxtjs.csv +59 -0
- package/skills-library/ui-ux-pro-max/data/stacks/react-native.csv +52 -0
- package/skills-library/ui-ux-pro-max/data/stacks/react.csv +54 -0
- package/skills-library/ui-ux-pro-max/data/stacks/shadcn.csv +61 -0
- package/skills-library/ui-ux-pro-max/data/stacks/svelte.csv +54 -0
- package/skills-library/ui-ux-pro-max/data/stacks/swiftui.csv +51 -0
- package/skills-library/ui-ux-pro-max/data/stacks/vue.csv +50 -0
- package/skills-library/ui-ux-pro-max/data/styles.csv +68 -0
- package/skills-library/ui-ux-pro-max/data/typography.csv +58 -0
- package/skills-library/ui-ux-pro-max/data/ui-reasoning.csv +101 -0
- package/skills-library/ui-ux-pro-max/data/ux-guidelines.csv +100 -0
- package/skills-library/ui-ux-pro-max/data/web-interface.csv +31 -0
- package/skills-library/wordpress-style-theme-components.md +1526 -0
- package/templates/ASSUMPTIONS.md +1 -1
- package/templates/DECISION_LOG.md +0 -1
- package/templates/phase-prompt.md +1 -1
- package/templates/phoenix-comparison.md +6 -6
- package/templates/skill-api-integration.md +106 -0
- package/templates/skill-architecture-pattern.md +92 -0
- package/templates/skill-debug-pattern.md +98 -0
- package/templates/skill-devops-recipe.md +107 -0
- package/templates/skill-general.md +65 -0
- package/templates/skill-ui-component.md +113 -0
- package/tools/uat-runner.py +179 -0
- package/version.json +7 -3
- package/workflows/handoff-session.md +2 -2
- package/workflows/new-project.md +2 -2
- package/workflows/plan-phase.md +1 -1
- package/.claude-plugin/plugin.json +0 -64
- package/skills-library/_general/methodology/LIVE_BREADCRUMB_PROTOCOL.md +0 -242
- package/skills-library/_general/methodology/llm-judge-memory-crud.md +0 -241
- package/skills-library/methodology/REFLEXION_MEMORY_PATTERN.md +0 -183
- package/skills-library/methodology/RESEARCH_BACKED_WORKFLOW_UPGRADE.md +0 -263
- package/skills-library/methodology/SABBATH_REST_PATTERN.md +0 -267
- package/skills-library/methodology/STONE_AND_SCAFFOLD.md +0 -220
- package/skills-library/specialists/api-architecture/api-designer.md +0 -49
- package/skills-library/specialists/api-architecture/graphql-architect.md +0 -49
- package/skills-library/specialists/api-architecture/mcp-developer.md +0 -51
- package/skills-library/specialists/api-architecture/microservices-architect.md +0 -50
- package/skills-library/specialists/api-architecture/websocket-engineer.md +0 -48
- package/skills-library/specialists/backend/django-expert.md +0 -52
- package/skills-library/specialists/backend/fastapi-expert.md +0 -52
- package/skills-library/specialists/backend/laravel-specialist.md +0 -52
- package/skills-library/specialists/backend/nestjs-expert.md +0 -51
- package/skills-library/specialists/backend/rails-expert.md +0 -53
- package/skills-library/specialists/backend/spring-boot-engineer.md +0 -56
- package/skills-library/specialists/data-ml/fine-tuning-expert.md +0 -48
- package/skills-library/specialists/data-ml/ml-pipeline.md +0 -47
- package/skills-library/specialists/data-ml/pandas-pro.md +0 -47
- package/skills-library/specialists/data-ml/rag-architect.md +0 -51
- package/skills-library/specialists/data-ml/spark-engineer.md +0 -47
- package/skills-library/specialists/frontend/angular-architect.md +0 -52
- package/skills-library/specialists/frontend/flutter-expert.md +0 -51
- package/skills-library/specialists/frontend/nextjs-developer.md +0 -54
- package/skills-library/specialists/frontend/react-native-expert.md +0 -50
- package/skills-library/specialists/frontend/vue-expert.md +0 -51
- package/skills-library/specialists/infrastructure/chaos-engineer.md +0 -74
- package/skills-library/specialists/infrastructure/cloud-architect.md +0 -70
- package/skills-library/specialists/infrastructure/database-optimizer.md +0 -64
- package/skills-library/specialists/infrastructure/devops-engineer.md +0 -70
- package/skills-library/specialists/infrastructure/kubernetes-specialist.md +0 -52
- package/skills-library/specialists/infrastructure/monitoring-expert.md +0 -70
- package/skills-library/specialists/infrastructure/sre-engineer.md +0 -70
- package/skills-library/specialists/infrastructure/terraform-engineer.md +0 -51
- package/skills-library/specialists/languages/cpp-pro.md +0 -74
- package/skills-library/specialists/languages/csharp-developer.md +0 -69
- package/skills-library/specialists/languages/dotnet-core-expert.md +0 -54
- package/skills-library/specialists/languages/golang-pro.md +0 -51
- package/skills-library/specialists/languages/java-architect.md +0 -49
- package/skills-library/specialists/languages/javascript-pro.md +0 -68
- package/skills-library/specialists/languages/kotlin-specialist.md +0 -68
- package/skills-library/specialists/languages/php-pro.md +0 -49
- package/skills-library/specialists/languages/python-pro.md +0 -52
- package/skills-library/specialists/languages/react-expert.md +0 -51
- package/skills-library/specialists/languages/rust-engineer.md +0 -50
- package/skills-library/specialists/languages/sql-pro.md +0 -56
- package/skills-library/specialists/languages/swift-expert.md +0 -69
- package/skills-library/specialists/languages/typescript-pro.md +0 -51
- package/skills-library/specialists/platform/atlassian-mcp.md +0 -52
- package/skills-library/specialists/platform/embedded-systems.md +0 -53
- package/skills-library/specialists/platform/game-developer.md +0 -53
- package/skills-library/specialists/platform/salesforce-developer.md +0 -53
- package/skills-library/specialists/platform/shopify-expert.md +0 -49
- package/skills-library/specialists/platform/wordpress-pro.md +0 -49
- package/skills-library/specialists/quality/code-documenter.md +0 -51
- package/skills-library/specialists/quality/code-reviewer.md +0 -67
- package/skills-library/specialists/quality/debugging-wizard.md +0 -51
- package/skills-library/specialists/quality/fullstack-guardian.md +0 -51
- package/skills-library/specialists/quality/legacy-modernizer.md +0 -50
- package/skills-library/specialists/quality/playwright-expert.md +0 -65
- package/skills-library/specialists/quality/spec-miner.md +0 -56
- package/skills-library/specialists/quality/test-master.md +0 -65
- package/skills-library/specialists/security/secure-code-guardian.md +0 -55
- package/skills-library/specialists/security/security-reviewer.md +0 -53
- package/skills-library/specialists/workflow/architecture-designer.md +0 -53
- package/skills-library/specialists/workflow/cli-developer.md +0 -70
- package/skills-library/specialists/workflow/feature-forge.md +0 -65
- package/skills-library/specialists/workflow/prompt-engineer.md +0 -54
- package/skills-library/specialists/workflow/the-fool.md +0 -62
- /package/skills-library/{performance → _general/performance}/cache-augmented-generation.md +0 -0
- /package/skills-library/{debugging → parallel-debug}/FAILURE_TAXONOMY_CLASSIFICATION.md +0 -0
- /package/skills-library/{debugging → parallel-debug}/THREE_AGENT_HYPOTHESIS_DEBUGGING.md +0 -0
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: mysql-to-pg-migration
|
|
3
|
+
category: database-solutions
|
|
4
|
+
version: 1.0.0
|
|
5
|
+
contributed: 2026-03-10
|
|
6
|
+
contributor: research
|
|
7
|
+
last_updated: 2026-03-10
|
|
8
|
+
tags: [mysql, postgresql, migration, pgloader, schema-conversion]
|
|
9
|
+
difficulty: hard
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
# MySQL to PostgreSQL Migration
|
|
13
|
+
|
|
14
|
+
## Problem
|
|
15
|
+
|
|
16
|
+
Migrating from MySQL to PostgreSQL is the most common enterprise database migration direction (validated by the $480K/year savings case study, 2026). Despite tooling like pgloader, 20% of translations require manual intervention — type mappings, stored procedure rewrites, and application code changes that tools miss.
|
|
17
|
+
## Solution Pattern
|
|
18
|
+
|
|
19
|
+
### Phase 1: Assessment
|
|
20
|
+
|
|
21
|
+
Before any migration, audit the source MySQL database:
|
|
22
|
+
|
|
23
|
+
```sql
|
|
24
|
+
-- Count tables, views, procedures, triggers
|
|
25
|
+
SELECT 'tables' AS type, COUNT(*) FROM information_schema.tables WHERE table_schema = 'mydb'
|
|
26
|
+
UNION ALL
|
|
27
|
+
SELECT 'views', COUNT(*) FROM information_schema.views WHERE table_schema = 'mydb'
|
|
28
|
+
UNION ALL
|
|
29
|
+
SELECT 'procedures', COUNT(*) FROM information_schema.routines WHERE routine_schema = 'mydb'
|
|
30
|
+
UNION ALL
|
|
31
|
+
SELECT 'triggers', COUNT(*) FROM information_schema.triggers WHERE trigger_schema = 'mydb';
|
|
32
|
+
|
|
33
|
+
-- Find unsigned columns (require upsizing)
|
|
34
|
+
SELECT table_name, column_name, column_type
|
|
35
|
+
FROM information_schema.columns
|
|
36
|
+
WHERE table_schema = 'mydb' AND column_type LIKE '%unsigned%';
|
|
37
|
+
|
|
38
|
+
-- Find ENUM columns (require CREATE TYPE)
|
|
39
|
+
SELECT table_name, column_name, column_type
|
|
40
|
+
FROM information_schema.columns
|
|
41
|
+
WHERE table_schema = 'mydb' AND data_type = 'enum';
|
|
42
|
+
|
|
43
|
+
-- Find zero-date values (will become NULL)
|
|
44
|
+
SELECT table_name, column_name
|
|
45
|
+
FROM information_schema.columns
|
|
46
|
+
WHERE table_schema = 'mydb' AND (data_type = 'datetime' OR data_type = 'timestamp');
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
### Phase 2: Schema Conversion
|
|
50
|
+
|
|
51
|
+
#### Core Type Translations
|
|
52
|
+
|
|
53
|
+
| MySQL | PostgreSQL | Notes |
|
|
54
|
+
|---|---|---|
|
|
55
|
+
| `INT AUTO_INCREMENT` | `SERIAL` or `GENERATED ALWAYS AS IDENTITY` | IDENTITY is SQL standard |
|
|
56
|
+
| `BIGINT AUTO_INCREMENT` | `BIGSERIAL` | |
|
|
57
|
+
| `TINYINT(1)` / `BOOL` | `BOOLEAN` | Validate no values > 1 |
|
|
58
|
+
| `TINYINT` (other) | `SMALLINT` | |
|
|
59
|
+
| `INT UNSIGNED` | `BIGINT` | Upsize for unsigned range |
|
|
60
|
+
| `DOUBLE` | `DOUBLE PRECISION` | |
|
|
61
|
+
| `DATETIME` | `TIMESTAMP` or `TIMESTAMPTZ` | Choose based on timezone needs |
|
|
62
|
+
| `ENUM('a','b','c')` | `CREATE TYPE myenum AS ENUM('a','b','c')` | One type per unique enum set |
|
|
63
|
+
| `` `backtick_quoted` `` | `"double_quoted"` | PG preserves case in quotes |
|
|
64
|
+
| `JSON` | `JSONB` | Upgrade to binary for indexing |
|
|
65
|
+
|
|
66
|
+
#### Syntax Translations (Application Code)
|
|
67
|
+
|
|
68
|
+
| MySQL | PostgreSQL | Notes |
|
|
69
|
+
|---|---|---|
|
|
70
|
+
| `IFNULL(a, b)` | `COALESCE(a, b)` | COALESCE is SQL standard |
|
|
71
|
+
| `IF(cond, a, b)` | `CASE WHEN cond THEN a ELSE b END` | |
|
|
72
|
+
| `LIMIT k, n` | `LIMIT n OFFSET k` | Argument order reverses! |
|
|
73
|
+
| `DATE_FORMAT(d, '%Y-%m')` | `TO_CHAR(d, 'YYYY-MM')` | Different format tokens |
|
|
74
|
+
| `GROUP_CONCAT(col)` | `STRING_AGG(col, ',')` | PG requires explicit separator |
|
|
75
|
+
| `CONCAT(a, b)` | `a \|\| b` | PG also supports CONCAT() |
|
|
76
|
+
| `NOW()` | `NOW()` | Same |
|
|
77
|
+
| `LOCATE(sub, str)` | `POSITION(sub IN str)` | |
|
|
78
|
+
| `json_extract(col, '$.key')` | `col->>'key'` | Simpler syntax in PG |
|
|
79
|
+
| `ON DUPLICATE KEY UPDATE` | `ON CONFLICT (col) DO UPDATE SET` | Different upsert syntax |
|
|
80
|
+
| `VALUES(col)` (in upsert) | `EXCLUDED.col` | Reference to proposed row |
|
|
81
|
+
| `INSERT IGNORE INTO` | `ON CONFLICT DO NOTHING` | |
|
|
82
|
+
|
|
83
|
+
### Phase 3: Automated Migration with pgloader
|
|
84
|
+
|
|
85
|
+
```lisp
|
|
86
|
+
-- pgloader.conf
|
|
87
|
+
LOAD DATABASE
|
|
88
|
+
FROM mysql://user:pass@localhost/mydb
|
|
89
|
+
INTO postgresql://user:pass@localhost/mydb_pg
|
|
90
|
+
|
|
91
|
+
WITH
|
|
92
|
+
include drop,
|
|
93
|
+
create tables,
|
|
94
|
+
create indexes,
|
|
95
|
+
reset sequences,
|
|
96
|
+
workers = 4,
|
|
97
|
+
concurrency = 2
|
|
98
|
+
|
|
99
|
+
-- Custom type overrides
|
|
100
|
+
CAST
|
|
101
|
+
type tinyint when (= 1 precision) to boolean using tinyint-to-boolean,
|
|
102
|
+
type int when unsigned to bigint,
|
|
103
|
+
type year to integer,
|
|
104
|
+
type datetime to timestamptz
|
|
105
|
+
|
|
106
|
+
-- Handle zero-dates
|
|
107
|
+
BEFORE LOAD DO
|
|
108
|
+
$$ ALTER DATABASE mydb_pg SET datestyle TO 'ISO, MDY'; $$
|
|
109
|
+
|
|
110
|
+
AFTER LOAD DO
|
|
111
|
+
$$ VACUUM ANALYZE; $$
|
|
112
|
+
;
|
|
113
|
+
```
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
# Run pgloader
|
|
117
|
+
pgloader pgloader.conf
|
|
118
|
+
|
|
119
|
+
# Verify
|
|
120
|
+
psql -d mydb_pg -c "SELECT schemaname, tablename FROM pg_tables WHERE schemaname = 'public';"
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
### Phase 4: Application Code Changes
|
|
124
|
+
|
|
125
|
+
1. **Connection driver:** `mysql2` → `pg` (or `postgres.js`)
|
|
126
|
+
2. **Parameter placeholders:** `?` → `$1, $2, $3` (numbered)
|
|
127
|
+
3. **Identifier quoting:** Backticks → double quotes (or remove)
|
|
128
|
+
4. **Boolean values:** `1/0` → `true/false`
|
|
129
|
+
5. **JSON access:** `JSON_EXTRACT(col, '$.key')` → `col->>'key'`
|
|
130
|
+
6. **Date formatting:** `DATE_FORMAT(d, '%Y-%m-%d')` → `TO_CHAR(d, 'YYYY-MM-DD')`
|
|
131
|
+
7. **String aggregation:** `GROUP_CONCAT(col SEPARATOR ',')` → `STRING_AGG(col::text, ',')`
|
|
132
|
+
8. **UPSERT:** `ON DUPLICATE KEY UPDATE` → `ON CONFLICT ... DO UPDATE SET`
|
|
133
|
+
9. **LIMIT syntax:** `LIMIT offset, count` → `LIMIT count OFFSET offset`
|
|
134
|
+
10. **RETURNING:** Can now use `INSERT ... RETURNING *` natively (was emulated)
|
|
135
|
+
|
|
136
|
+
### Phase 5: Post-Migration Validation
|
|
137
|
+
|
|
138
|
+
```bash
|
|
139
|
+
# Compare table counts
|
|
140
|
+
mysql -u user -p mydb -e "SELECT COUNT(*) FROM users;"
|
|
141
|
+
psql -d mydb_pg -c "SELECT COUNT(*) FROM users;"
|
|
142
|
+
|
|
143
|
+
# Compare row counts for all tables
|
|
144
|
+
psql -d mydb_pg -c "
|
|
145
|
+
SELECT schemaname, relname, n_live_tup
|
|
146
|
+
FROM pg_stat_user_tables
|
|
147
|
+
ORDER BY n_live_tup DESC;
|
|
148
|
+
"
|
|
149
|
+
|
|
150
|
+
# Run VACUUM ANALYZE on all tables
|
|
151
|
+
psql -d mydb_pg -c "VACUUM ANALYZE;"
|
|
152
|
+
|
|
153
|
+
# Verify sequences are correct
|
|
154
|
+
psql -d mydb_pg -c "
|
|
155
|
+
SELECT sequencename, last_value
|
|
156
|
+
FROM pg_sequences
|
|
157
|
+
WHERE schemaname = 'public';
|
|
158
|
+
"
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
## Common Breakage Points
|
|
162
|
+
|
|
163
|
+
1. **Timezone drift:** MySQL DATETIME has no timezone; PG TIMESTAMPTZ is UTC-aware. Audit trail timestamps may shift.
|
|
164
|
+
2. **Zero-dates:** MySQL `0000-00-00` → NULL in PG. Application code expecting these dates will break.
|
|
165
|
+
3. **Case sensitivity:** MySQL table names are case-insensitive on Windows; PG is always case-sensitive. Verify all table references.
|
|
166
|
+
4. **ENUM ordering:** MySQL ENUMs have implicit ordering; PG ENUMs have explicit ordering. Sorts may change.
|
|
167
|
+
5. **Implicit type casts:** MySQL silently casts strings to numbers in comparisons; PG raises errors.
|
|
168
|
+
6. **GROUP BY strictness:** PG requires all non-aggregated columns in GROUP BY; MySQL's `ONLY_FULL_GROUP_BY` is optional.
|
|
169
|
+
|
|
170
|
+
## When to Use
|
|
171
|
+
|
|
172
|
+
- Migrating from MySQL to PostgreSQL (any direction)
|
|
173
|
+
- Planning a database migration for `/fire-resurrect --migrate`
|
|
174
|
+
- Evaluating migration complexity before committing
|
|
175
|
+
|
|
176
|
+
## When NOT to Use
|
|
177
|
+
|
|
178
|
+
- MySQL-to-MySQL upgrades (different problem)
|
|
179
|
+
- Migrating to/from NoSQL
|
|
180
|
+
- Small SQLite databases (use sqlite-to-pg-migration instead)
|
|
181
|
+
|
|
182
|
+
## Related Skills
|
|
183
|
+
|
|
184
|
+
- [sql-dialect-compatibility-matrix](sql-dialect-compatibility-matrix.md)
|
|
185
|
+
- [data-type-mapping-reference](data-type-mapping-reference.md)
|
|
186
|
+
- [pg-to-mysql-schema-migration-methodology](pg-to-mysql-schema-migration-methodology.md) — reverse direction
|
|
187
|
+
- [sqlite-to-pg-migration](sqlite-to-pg-migration.md)
|
|
188
|
+
|
|
189
|
+
## References
|
|
190
|
+
|
|
191
|
+
- "The MySQL-to-Postgres Migration That Saved $480K/Year" (Medium, 2026)
|
|
192
|
+
- "I Migrated 400M Rows — Here's What Actually Broke" (Medium, 2026)
|
|
193
|
+
- pgloader documentation (pgloader.readthedocs.io)
|
|
194
|
+
- AI2sql MySQL-to-PostgreSQL conversion guide (2026)
|
|
195
|
+
- Percona pgloader guide (percona.com/blog)
|
|
@@ -0,0 +1,193 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: orm-schema-portability
|
|
3
|
+
category: database-solutions
|
|
4
|
+
version: 1.0.0
|
|
5
|
+
contributed: 2026-03-10
|
|
6
|
+
contributor: research
|
|
7
|
+
last_updated: 2026-03-10
|
|
8
|
+
tags: [orm, prisma, knex, drizzle, typeorm, sequelize, django, portability, migration]
|
|
9
|
+
difficulty: medium
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
# ORM Schema Portability
|
|
13
|
+
|
|
14
|
+
## Problem
|
|
15
|
+
|
|
16
|
+
Developers assume ORMs abstract away database differences. They don't. Every ORM leaks dialect-specific behavior for arrays, enums, JSON querying, full-text search, and migrations. Switching databases after building on ORM-specific features requires significant rework that isn't obvious until migration day.
|
|
17
|
+
## ORM Portability Comparison
|
|
18
|
+
|
|
19
|
+
| Dimension | Prisma | Knex.js | Drizzle | TypeORM | Sequelize | Django |
|
|
20
|
+
|---|---|---|---|---|---|---|
|
|
21
|
+
| **Schema portability** | Single provider | N/A (query builder) | Separate per dialect | Mostly portable | Mostly portable | Fully portable |
|
|
22
|
+
| **Migration portability** | None (SQL files) | Partial (schema builder) | None (dialect SQL) | Partial (auto-gen) | Low | High (Python) |
|
|
23
|
+
| **Array support** | PG only | N/A | Dialect-specific | PG only | PG only | PG only |
|
|
24
|
+
| **JSON support** | PG, MySQL (recent SQLite) | N/A | Dialect-specific | All (simple-json) | PG, MySQL, SQLite | All (since 3.1) |
|
|
25
|
+
| **Enum support** | PG, MySQL | N/A | Dialect-specific | PG, MySQL | PG, MySQL, SQLite | All (CharField) |
|
|
26
|
+
| **Raw SQL portability** | None | None | Param only | None | None | Partial |
|
|
27
|
+
| **Switching effort** | **High** | **Medium** | **Very High** | **Medium** | **Medium** | **Low** |
|
|
28
|
+
| **Best for multi-DB** | No | Yes | No | Moderate | Moderate | **Yes** |
|
|
29
|
+
|
|
30
|
+
## Per-ORM Details
|
|
31
|
+
|
|
32
|
+
### Prisma — Single Provider, No Switching
|
|
33
|
+
|
|
34
|
+
**What it abstracts:** CRUD, relations, connection pooling, type generation.
|
|
35
|
+
|
|
36
|
+
**What breaks when switching:**
|
|
37
|
+
- Schema is inherently single-provider (`provider = "postgresql"` in schema.prisma)
|
|
38
|
+
- No `provider = "universal"` — community request since 2020, still unresolved
|
|
39
|
+
- Enum, JSON, scalar list support varies by provider
|
|
40
|
+
- Migrations generate provider-specific SQL — not reusable across databases
|
|
41
|
+
- `$queryRaw` uses `$1` for PG, `?` for MySQL — dialect-dependent
|
|
42
|
+
|
|
43
|
+
**Portable pattern:** Maintain separate schema files per provider. Share application code.
|
|
44
|
+
|
|
45
|
+
### Knex.js — Best JS/TS Option for Portability
|
|
46
|
+
|
|
47
|
+
**What it abstracts:** Query building, schema builder DDL, connection pooling, parameter binding.
|
|
48
|
+
|
|
49
|
+
**What breaks when switching:**
|
|
50
|
+
- SQLite's limited ALTER TABLE (Knex emulates with temp table + copy)
|
|
51
|
+
- `RETURNING` is PG/SQLite only
|
|
52
|
+
- `knex.raw()` completely kills portability
|
|
53
|
+
- Result shape differs by dialect (`{ rows: [...] }` vs `[[...], fields]`)
|
|
54
|
+
- LIMIT/OFFSET string values accepted by PG, rejected by MySQL
|
|
55
|
+
|
|
56
|
+
**Portable pattern:** Use schema builder API exclusively. Avoid `knex.raw()`. Coerce LIMIT/OFFSET to integers.
|
|
57
|
+
|
|
58
|
+
**MINISTRY-LMS approach:** Knex migrations with conditional DDL:
|
|
59
|
+
```javascript
|
|
60
|
+
const isPostgres = knex.client.config.client === 'pg';
|
|
61
|
+
if (isPostgres) {
|
|
62
|
+
table.uuid('id').primary().defaultTo(knex.raw('gen_random_uuid()'));
|
|
63
|
+
table.jsonb('settings');
|
|
64
|
+
} else {
|
|
65
|
+
table.uuid('id').primary();
|
|
66
|
+
table.json('settings');
|
|
67
|
+
}
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
### Drizzle — Intentionally Non-Portable
|
|
71
|
+
|
|
72
|
+
**What it abstracts:** Type-safe query building, relational queries, driver adapters.
|
|
73
|
+
|
|
74
|
+
**What breaks when switching:**
|
|
75
|
+
- **Schema definitions are NOT portable.** Separate imports: `pgTable`, `mysqlTable`, `sqliteTable`
|
|
76
|
+
- Column types differ per dialect (e.g., `serial` in PG vs `int` + `autoIncrement` in MySQL)
|
|
77
|
+
- Migrations generate dialect-specific SQL
|
|
78
|
+
|
|
79
|
+
**Why it's designed this way:** Drizzle is "SQL with types" — it deliberately exposes dialect differences for maximum control and type safety. The trade-off is zero cross-dialect portability.
|
|
80
|
+
|
|
81
|
+
**Portable pattern:** Share column definitions via spread syntax; rewrite table definitions per dialect.
|
|
82
|
+
|
|
83
|
+
### TypeORM — Moderate Portability
|
|
84
|
+
|
|
85
|
+
**What it abstracts:** Entity decorators map to appropriate types, repository pattern, QueryBuilder.
|
|
86
|
+
|
|
87
|
+
**What breaks when switching:**
|
|
88
|
+
- `array: true` is PG/CockroachDB only
|
|
89
|
+
- `jsonb` is PG only; MySQL uses `json`; SQLite stores as text
|
|
90
|
+
- `unsigned` modifier is MySQL only
|
|
91
|
+
- Enum+Array combination is problematic on PG
|
|
92
|
+
- `@CreateDateColumn` precision differs
|
|
93
|
+
|
|
94
|
+
**Portable pattern:** Use `simple-array`, `simple-json`, `simple-enum` types (stored as strings). Avoid native types.
|
|
95
|
+
|
|
96
|
+
### Sequelize — Moderate Portability
|
|
97
|
+
|
|
98
|
+
**What it abstracts:** Model definition, query interface, associations, transactions.
|
|
99
|
+
|
|
100
|
+
**What breaks when switching:**
|
|
101
|
+
- `DataTypes.ARRAY` is PG only
|
|
102
|
+
- `DataTypes.JSONB` is PG only
|
|
103
|
+
- `CITEXT` is PG/SQLite only
|
|
104
|
+
- ENUM storage differs (PG: CREATE TYPE, MySQL: inline, SQLite: CHECK)
|
|
105
|
+
- v7 moved dialects to separate packages (breaking change from v6)
|
|
106
|
+
|
|
107
|
+
**Portable pattern:** Stick to `DataTypes.STRING`, `INTEGER`, `BOOLEAN`, `DATE`, `JSON` (not JSONB), `TEXT`.
|
|
108
|
+
|
|
109
|
+
### Django — Most Portable
|
|
110
|
+
|
|
111
|
+
**What it abstracts:** Model definitions, QuerySet API, migration framework, admin interface.
|
|
112
|
+
|
|
113
|
+
**What breaks when switching:**
|
|
114
|
+
- `ArrayField` is PG only (`django.contrib.postgres`)
|
|
115
|
+
- `HStoreField` is PG only
|
|
116
|
+
- Full-text search (`SearchVector`, `SearchRank`) is PG only
|
|
117
|
+
- Range fields are PG only
|
|
118
|
+
|
|
119
|
+
**Portable pattern:** Avoid `django.contrib.postgres`. Use `JSONField` (cross-DB since 3.1). Use `CharField(choices=...)` instead of custom ENUM types.
|
|
120
|
+
|
|
121
|
+
**Why Django wins:** Python-based migrations (not raw SQL) are inherently backend-agnostic. `%s` parameter placeholders are translated internally by Django.
|
|
122
|
+
|
|
123
|
+
## The Safest Portable Subset
|
|
124
|
+
|
|
125
|
+
These ORM types work identically across PG, MySQL, SQLite with zero translation in ANY ORM:
|
|
126
|
+
|
|
127
|
+
```
|
|
128
|
+
string / VARCHAR(n) — where n ≤ 255
|
|
129
|
+
integer / INT — signed 32-bit
|
|
130
|
+
float / DOUBLE — 8-byte floating point
|
|
131
|
+
boolean / BOOLEAN — true/false (ORM handles TINYINT mapping)
|
|
132
|
+
text / TEXT — unlimited string
|
|
133
|
+
timestamp / DATETIME — ORM handles dialect differences
|
|
134
|
+
uuid-as-string / CHAR(36) — generate in app code
|
|
135
|
+
json-as-text / JSON — basic JSON (no JSONB indexing)
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
**Avoid for portability:** Arrays, JSONB, native ENUM, range types, full-text search, geometric types, HSTORE.
|
|
139
|
+
|
|
140
|
+
## Decision Matrix: Choosing an ORM for Multi-DB
|
|
141
|
+
|
|
142
|
+
| If you need... | Use... | Why |
|
|
143
|
+
|---|---|---|
|
|
144
|
+
| Maximum portability (Python) | **Django** | Python migrations, internal param translation |
|
|
145
|
+
| Maximum portability (JS/TS) | **Knex.js** | Query builder, not ORM — minimal abstraction leak |
|
|
146
|
+
| Type safety over portability | **Drizzle** | Explicit dialect awareness, best TypeScript DX |
|
|
147
|
+
| Quick prototyping | **Prisma** | Best DX, but locked to one provider |
|
|
148
|
+
| Legacy enterprise | **TypeORM** or **Sequelize** | Broad dialect support, mature ecosystem |
|
|
149
|
+
|
|
150
|
+
## Migration State Continuity
|
|
151
|
+
|
|
152
|
+
When rebuilding an app (e.g., `/fire-resurrect`), the ORM's migration tracking table lives IN the database:
|
|
153
|
+
|
|
154
|
+
| ORM | Migration Table | What It Tracks |
|
|
155
|
+
|---|---|---|
|
|
156
|
+
| Prisma | `_prisma_migrations` | Applied migration names + timestamps |
|
|
157
|
+
| Knex | `knex_migrations` | Batch number + migration name |
|
|
158
|
+
| Sequelize | `SequelizeMeta` | Migration filenames |
|
|
159
|
+
| TypeORM | `migrations` | Timestamp + name |
|
|
160
|
+
| Django | `django_migrations` | App + name + applied timestamp |
|
|
161
|
+
|
|
162
|
+
**Key insight:** If you point a new project at an existing database with the same migration files, the ORM knows which migrations have already run. No re-creation, no data loss.
|
|
163
|
+
|
|
164
|
+
**For "reuse" strategy in fire-resurrect:** Copy migration files to new project → point at existing DB → `migrate:latest` runs only NEW migrations.
|
|
165
|
+
|
|
166
|
+
## When to Use
|
|
167
|
+
|
|
168
|
+
- Choosing an ORM for a new multi-database project
|
|
169
|
+
- Auditing existing ORM schema for portability issues before migration
|
|
170
|
+
- Planning the VISION phase of `/fire-resurrect` with `--migrate`
|
|
171
|
+
- Understanding why a database switch broke application code
|
|
172
|
+
|
|
173
|
+
## When NOT to Use
|
|
174
|
+
|
|
175
|
+
- Single-database projects with no migration plans
|
|
176
|
+
- Raw SQL projects (use sql-dialect-compatibility-matrix instead)
|
|
177
|
+
- NoSQL ORMs (Mongoose, etc.)
|
|
178
|
+
|
|
179
|
+
## Related Skills
|
|
180
|
+
|
|
181
|
+
- [sql-dialect-compatibility-matrix](sql-dialect-compatibility-matrix.md)
|
|
182
|
+
- [data-type-mapping-reference](data-type-mapping-reference.md)
|
|
183
|
+
- [pg-to-mysql-schema-migration-methodology](pg-to-mysql-schema-migration-methodology.md)
|
|
184
|
+
|
|
185
|
+
## References
|
|
186
|
+
|
|
187
|
+
- Prisma multiple database support limitations (issue #1487)
|
|
188
|
+
- Bytebase — "Drizzle vs Prisma" (2026)
|
|
189
|
+
- TheDataGuy — "Node.js ORMs in 2025" (Dec 2025)
|
|
190
|
+
- MINISTRY-LMS Knex migration patterns (production-proven, 2026)
|
|
191
|
+
- Django ORM comparison (Paolo Melchiorre, 2025)
|
|
192
|
+
- Drizzle ORM schema declaration docs
|
|
193
|
+
- Sequelize v7 dialect-specific documentation
|
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: persistent-analysis-storage
|
|
3
|
+
category: database-solutions
|
|
4
|
+
version: 1.0.0
|
|
5
|
+
contributed: 2026-03-01
|
|
6
|
+
contributor: scribe-bible
|
|
7
|
+
last_updated: 2026-03-01
|
|
8
|
+
contributors:
|
|
9
|
+
- scribe-bible
|
|
10
|
+
tags: [prisma, postgresql, persistence, favorites, sharing, nanoid, cursor-pagination, dual-storage]
|
|
11
|
+
difficulty: medium
|
|
12
|
+
usage_count: 0
|
|
13
|
+
success_rate: 100
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
# Persistent Analysis Storage
|
|
17
|
+
|
|
18
|
+
## Problem
|
|
19
|
+
|
|
20
|
+
AI-powered analysis features (deep research, recursive reasoning, multi-step pipelines) produce expensive results that take 30-120+ seconds and significant API cost. Users need to:
|
|
21
|
+
|
|
22
|
+
1. **Save results permanently** to their account (not just browser localStorage)
|
|
23
|
+
2. **Favorite** important analyses for quick access
|
|
24
|
+
3. **Share publicly** via short links (without requiring recipient login)
|
|
25
|
+
4. **Browse history** with filtering and pagination
|
|
26
|
+
5. **Maintain anonymous fallback** — localStorage history works without login
|
|
27
|
+
|
|
28
|
+
Without DB persistence, results vanish on browser clear. Without dual-storage, unauthenticated users get no history at all.
|
|
29
|
+
|
|
30
|
+
## Solution Pattern
|
|
31
|
+
|
|
32
|
+
Implement a **dual-storage architecture** with localStorage as the anonymous/immediate layer and PostgreSQL (via Prisma) as the authenticated persistent layer. Each layer serves a different purpose:
|
|
33
|
+
|
|
34
|
+
- **localStorage**: Instant, no-auth, limited to ~50 items, browser-scoped
|
|
35
|
+
- **Database**: Permanent, auth-required, unlimited, supports sharing/favorites
|
|
36
|
+
|
|
37
|
+
The key insight is these layers are **complementary, not competing** — localStorage provides instant gratification while DB provides permanence. The UI presents both via a tabbed sidebar.
|
|
38
|
+
|
|
39
|
+
## Code Example
|
|
40
|
+
|
|
41
|
+
### Prisma Model
|
|
42
|
+
|
|
43
|
+
```prisma
|
|
44
|
+
model RlmAnalysis {
|
|
45
|
+
id String @id @default(uuid())
|
|
46
|
+
userId String
|
|
47
|
+
query String
|
|
48
|
+
analysisType String
|
|
49
|
+
result String @db.Text
|
|
50
|
+
trajectoryId String
|
|
51
|
+
trajectory String? @db.Text // JSON stringified steps
|
|
52
|
+
tokenUsage String? // JSON stringified usage
|
|
53
|
+
durationSeconds Float
|
|
54
|
+
translation String @default("kjv")
|
|
55
|
+
isFavorite Boolean @default(false)
|
|
56
|
+
isPublic Boolean @default(false)
|
|
57
|
+
shareSlug String? @unique // nanoid(8) generated on first share
|
|
58
|
+
createdAt DateTime @default(now())
|
|
59
|
+
updatedAt DateTime @updatedAt
|
|
60
|
+
user User @relation(fields: [userId], references: [id])
|
|
61
|
+
|
|
62
|
+
@@index([userId, createdAt])
|
|
63
|
+
@@index([userId, isFavorite])
|
|
64
|
+
@@index([analysisType])
|
|
65
|
+
}
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
### Storage Service (CRUD + Sharing)
|
|
69
|
+
|
|
70
|
+
```typescript
|
|
71
|
+
// Toggle public sharing — generates a short slug on first share
|
|
72
|
+
export async function toggleShare(id: string, userId: string) {
|
|
73
|
+
const analysis = await prisma.analysis.findUnique({ where: { id } });
|
|
74
|
+
if (!analysis || analysis.userId !== userId) return null;
|
|
75
|
+
|
|
76
|
+
const isPublic = !analysis.isPublic;
|
|
77
|
+
const shareSlug = isPublic && !analysis.shareSlug ? nanoid(8) : analysis.shareSlug;
|
|
78
|
+
|
|
79
|
+
return prisma.analysis.update({
|
|
80
|
+
where: { id },
|
|
81
|
+
data: { isPublic, shareSlug },
|
|
82
|
+
});
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
// Cursor-based pagination (better than offset for large sets)
|
|
86
|
+
export async function listAnalyses(options: ListOptions) {
|
|
87
|
+
const { userId, type, favoritesOnly, limit = 20, cursor } = options;
|
|
88
|
+
const where: any = { userId };
|
|
89
|
+
if (type) where.analysisType = type;
|
|
90
|
+
if (favoritesOnly) where.isFavorite = true;
|
|
91
|
+
|
|
92
|
+
const analyses = await prisma.analysis.findMany({
|
|
93
|
+
where,
|
|
94
|
+
orderBy: { createdAt: 'desc' },
|
|
95
|
+
take: limit + 1, // Fetch one extra to detect hasMore
|
|
96
|
+
...(cursor ? { cursor: { id: cursor }, skip: 1 } : {}),
|
|
97
|
+
select: { id: true, query: true, analysisType: true, /* ... */ },
|
|
98
|
+
});
|
|
99
|
+
|
|
100
|
+
const hasMore = analyses.length > limit;
|
|
101
|
+
const items = hasMore ? analyses.slice(0, limit) : analyses;
|
|
102
|
+
return { items, nextCursor: hasMore ? items[items.length - 1].id : null, hasMore };
|
|
103
|
+
}
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
### API Endpoints (7 routes)
|
|
107
|
+
|
|
108
|
+
```typescript
|
|
109
|
+
// Auth-required endpoints
|
|
110
|
+
router.post('/saved', authenticateToken, saveHandler); // Save analysis
|
|
111
|
+
router.get('/saved', authenticateToken, listHandler); // List with filters
|
|
112
|
+
router.get('/saved/:id', authenticateToken, getHandler); // Get single
|
|
113
|
+
router.delete('/saved/:id', authenticateToken, deleteHandler);// Delete
|
|
114
|
+
router.post('/saved/:id/favorite', authenticateToken, favHandler); // Toggle favorite
|
|
115
|
+
router.post('/saved/:id/share', authenticateToken, shareHandler); // Toggle share
|
|
116
|
+
|
|
117
|
+
// Public endpoint (no auth)
|
|
118
|
+
router.get('/shared/:slug', sharedHandler); // View shared analysis
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
### Frontend Hook (Dual Storage)
|
|
122
|
+
|
|
123
|
+
```typescript
|
|
124
|
+
// localStorage for anonymous history
|
|
125
|
+
const [history, setHistory] = useState<HistoryItem[]>(loadHistory);
|
|
126
|
+
|
|
127
|
+
// DB-backed for authenticated persistence
|
|
128
|
+
const saveToDb = useCallback(async (result: AnalysisResult) => {
|
|
129
|
+
const res = await fetch(`${API_BASE}/api/saved`, {
|
|
130
|
+
method: 'POST',
|
|
131
|
+
headers: { 'Content-Type': 'application/json', ...getAuthHeaders() },
|
|
132
|
+
body: JSON.stringify(result),
|
|
133
|
+
});
|
|
134
|
+
if (!res.ok) return null;
|
|
135
|
+
// Mark in local history as saved (cross-reference)
|
|
136
|
+
setHistory(prev => prev.map(h =>
|
|
137
|
+
h.trajectoryId === result.trajectoryId ? { ...h, savedToDb: true } : h
|
|
138
|
+
));
|
|
139
|
+
return (await res.json()).data;
|
|
140
|
+
}, []);
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
### Tabbed Sidebar UI
|
|
144
|
+
|
|
145
|
+
```tsx
|
|
146
|
+
{/* Tab buttons */}
|
|
147
|
+
<button onClick={() => setSidebarTab('recent')}
|
|
148
|
+
className={sidebarTab === 'recent' ? 'active' : ''}>
|
|
149
|
+
Recent ({history.length})
|
|
150
|
+
</button>
|
|
151
|
+
<button onClick={() => { setSidebarTab('saved'); loadSavedAnalyses(); }}
|
|
152
|
+
className={sidebarTab === 'saved' ? 'active' : ''}>
|
|
153
|
+
Saved ({savedAnalyses.length})
|
|
154
|
+
</button>
|
|
155
|
+
|
|
156
|
+
{/* Tab content */}
|
|
157
|
+
{sidebarTab === 'recent' ? (
|
|
158
|
+
// localStorage items with "saved" badge
|
|
159
|
+
history.map(item => <HistoryItem key={item.id} item={item} />)
|
|
160
|
+
) : (
|
|
161
|
+
// DB-backed items with favorite/share/delete actions
|
|
162
|
+
savedAnalyses.map(item => <SavedItem key={item.id} item={item} />)
|
|
163
|
+
)}
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
## Implementation Steps
|
|
167
|
+
|
|
168
|
+
1. Add Prisma model with indexes on userId+createdAt, userId+isFavorite, and unique shareSlug
|
|
169
|
+
2. Create storage service with CRUD + toggleFavorite + toggleShare (nanoid for slugs)
|
|
170
|
+
3. Add 7 API routes (6 auth-required + 1 public shared endpoint)
|
|
171
|
+
4. Extend frontend hook with DB persistence methods alongside existing localStorage
|
|
172
|
+
5. Add tabbed sidebar UI (Recent/Saved) with action buttons on saved items
|
|
173
|
+
6. Cross-reference: mark localStorage items as "savedToDb" when saved to DB
|
|
174
|
+
|
|
175
|
+
## When to Use
|
|
176
|
+
|
|
177
|
+
- AI analysis features that produce expensive, non-reproducible results
|
|
178
|
+
- Any feature where users want to bookmark/favorite results for later
|
|
179
|
+
- When public sharing via short links is needed (portfolios, collaboration)
|
|
180
|
+
- Dual anonymous + authenticated experience (localStorage fallback)
|
|
181
|
+
- Large result sets needing cursor-based pagination
|
|
182
|
+
|
|
183
|
+
## When NOT to Use
|
|
184
|
+
|
|
185
|
+
- Simple caching (use AI_RESPONSE_DATABASE_CACHING skill instead)
|
|
186
|
+
- Ephemeral data that doesn't need user ownership (use Redis/in-memory)
|
|
187
|
+
- When results are cheap to recompute (no persistence needed)
|
|
188
|
+
- Single-user apps with no sharing requirement (localStorage may suffice)
|
|
189
|
+
|
|
190
|
+
## Common Mistakes
|
|
191
|
+
|
|
192
|
+
- Using offset pagination instead of cursor-based (degrades at scale)
|
|
193
|
+
- Generating share slugs eagerly instead of on first share toggle (wasted IDs)
|
|
194
|
+
- Forgetting to handle the "not found OR not authorized" case (leaks existence info)
|
|
195
|
+
- Not providing localStorage fallback for unauthenticated users
|
|
196
|
+
- Storing large JSON blobs (trajectory, tokenUsage) as regular String instead of @db.Text
|
|
197
|
+
|
|
198
|
+
## Related Skills
|
|
199
|
+
|
|
200
|
+
- [AI_RESPONSE_DATABASE_CACHING](AI_RESPONSE_DATABASE_CACHING.md) - Cache-first pattern for avoiding recomputation
|
|
201
|
+
- cursor-pagination - Efficient large dataset browsing pattern
|
|
202
|
+
|
|
203
|
+
## References
|
|
204
|
+
|
|
205
|
+
- nanoid: https://github.com/ai/nanoid — short unique ID generation
|
|
206
|
+
- Prisma cursor pagination: https://www.prisma.io/docs/concepts/components/prisma-client/pagination#cursor-based-pagination
|
|
207
|
+
- Contributed from: scribe-bible (Phase 2 — Persistent Analysis Storage)
|