insforge 0.3.3 → 1.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude-plugin/marketplace.json +20 -0
- package/.dockerignore +60 -57
- package/.env.example +84 -49
- package/.github/ISSUE_TEMPLATE/bug_report.yml +36 -83
- package/.github/ISSUE_TEMPLATE/config.yml +11 -11
- package/.github/ISSUE_TEMPLATE/feature_request.yml +26 -79
- package/.github/PULL_REQUEST_TEMPLATE.md +7 -0
- package/.github/copilot-instructions.md +146 -146
- package/.github/workflows/build-image.yml +66 -65
- package/.github/workflows/ci-premerge-check.yml +23 -23
- package/.github/workflows/e2e.yml +63 -0
- package/.github/workflows/lint-and-format.yml +32 -32
- package/.prettierignore +64 -64
- package/CHANGELOG.md +44 -3
- package/CLAUDE_PLUGIN.md +104 -0
- package/CODE_OF_CONDUCT.md +128 -0
- package/CONTRIBUTING.md +125 -125
- package/Dockerfile +30 -27
- package/GITHUB_OAUTH_SETUP.md +49 -49
- package/GOOGLE_OAUTH_SETUP.md +148 -148
- package/LICENSE +201 -201
- package/README.md +182 -134
- package/assets/Dark.svg +23 -23
- package/assets/mcpInstallv2.png +0 -0
- package/assets/sampleResponse.png +0 -0
- package/auth/index.html +13 -0
- package/auth/package.json +28 -0
- package/auth/public/favicon.ico +0 -0
- package/auth/src/App.tsx +33 -0
- package/auth/src/components/ErrorCard.tsx +37 -0
- package/auth/src/components/Layout.tsx +13 -0
- package/auth/src/index.css +19 -0
- package/auth/src/lib/broadcastService.ts +117 -0
- package/auth/src/lib/utils.ts +11 -0
- package/auth/src/main.tsx +22 -0
- package/auth/src/pages/ForgotPasswordPage.tsx +11 -0
- package/auth/src/pages/ResetPasswordPage.tsx +11 -0
- package/auth/src/pages/SignInPage.tsx +60 -0
- package/auth/src/pages/SignUpPage.tsx +60 -0
- package/auth/src/pages/VerifyEmailPage.tsx +20 -0
- package/auth/src/vite-env.d.ts +10 -0
- package/auth/tsconfig.json +32 -0
- package/auth/tsconfig.node.json +11 -0
- package/auth/vite.config.ts +25 -0
- package/backend/package.json +78 -75
- package/backend/src/api/{middleware → middlewares}/auth.ts +8 -9
- package/backend/src/api/middlewares/rate-limiters.ts +127 -0
- package/backend/src/api/routes/{ai.ts → ai/index.routes.ts} +22 -26
- package/backend/src/api/routes/auth/index.routes.ts +667 -0
- package/backend/src/api/routes/auth/oauth.routes.ts +473 -0
- package/backend/src/api/routes/{database.advance.ts → database/advance.routes.ts} +128 -65
- package/backend/src/api/routes/database/index.routes.ts +90 -0
- package/backend/src/api/routes/{database.records.ts → database/records.routes.ts} +26 -12
- package/backend/src/api/routes/{database.tables.ts → database/tables.routes.ts} +6 -23
- package/backend/src/api/routes/docs/index.routes.ts +75 -0
- package/backend/src/api/routes/email/index.routes.ts +35 -0
- package/backend/src/api/routes/functions/index.routes.ts +194 -0
- package/backend/src/api/routes/{logs.ts → logs/index.routes.ts} +25 -30
- package/backend/src/api/routes/{metadata.ts → metadata/index.routes.ts} +33 -31
- package/backend/src/api/routes/realtime/channels.routes.ts +81 -0
- package/backend/src/api/routes/realtime/index.routes.ts +12 -0
- package/backend/src/api/routes/realtime/messages.routes.ts +48 -0
- package/backend/src/api/routes/realtime/permissions.routes.ts +19 -0
- package/backend/src/api/routes/{secrets.ts → secrets/index.routes.ts} +27 -22
- package/backend/src/api/routes/{storage.ts → storage/index.routes.ts} +48 -61
- package/backend/src/api/routes/usage/index.routes.ts +91 -0
- package/backend/src/infra/config/app.config.ts +51 -0
- package/backend/src/infra/database/database.manager.ts +182 -0
- package/backend/{migrations → src/infra/database/migrations}/000_create-base-tables.sql +141 -141
- package/backend/{migrations → src/infra/database/migrations}/001_create-helper-functions.sql +40 -40
- package/backend/{migrations → src/infra/database/migrations}/002_rename-auth-tables.sql +29 -29
- package/backend/{migrations → src/infra/database/migrations}/003_create-users-table.sql +55 -55
- package/backend/{migrations → src/infra/database/migrations}/004_add-reload-postgrest-func.sql +23 -23
- package/backend/{migrations → src/infra/database/migrations}/005_enable-project-admin-modify-users.sql +29 -29
- package/backend/{migrations → src/infra/database/migrations}/006_modify-ai-usage-table.sql +24 -24
- package/backend/{migrations → src/infra/database/migrations}/007_drop-metadata-table.sql +1 -1
- package/backend/{migrations → src/infra/database/migrations}/008_add-system-tables.sql +76 -76
- package/backend/{migrations → src/infra/database/migrations}/009_add-function-secrets.sql +23 -23
- package/backend/{migrations → src/infra/database/migrations}/010_modify-ai-config-modalities.sql +93 -93
- package/backend/{migrations → src/infra/database/migrations}/011_refactor-secrets-table.sql +15 -15
- package/backend/{migrations → src/infra/database/migrations}/012_add-storage-uploaded-by.sql +7 -7
- package/backend/src/infra/database/migrations/013_create-auth-schema-functions.sql +44 -0
- package/backend/src/infra/database/migrations/014_add-updated-at-trigger-user-table.sql +8 -0
- package/backend/src/infra/database/migrations/015_create-auth-config-and-email-otp-tables.sql +60 -0
- package/backend/src/infra/database/migrations/016_update-auth-config-and-email-otp.sql +24 -0
- package/backend/src/infra/database/migrations/017_create-realtime-schema.sql +233 -0
- package/backend/src/infra/realtime/realtime.manager.ts +246 -0
- package/backend/src/infra/realtime/webhook-sender.ts +82 -0
- package/backend/src/{core/secrets/encryption.ts → infra/security/encryption.manager.ts} +3 -2
- package/backend/src/infra/security/token.manager.ts +219 -0
- package/backend/src/infra/socket/socket.manager.ts +522 -0
- package/backend/src/providers/ai/openrouter.provider.ts +380 -0
- package/backend/src/providers/email/base.provider.ts +38 -0
- package/backend/src/providers/email/cloud.provider.ts +271 -0
- package/backend/src/{core/logs/providers → providers/logs}/base.provider.ts +11 -11
- package/backend/src/{core/logs/providers → providers/logs}/cloudwatch.provider.ts +61 -38
- package/backend/src/providers/logs/local.provider.ts +185 -0
- package/backend/src/providers/oauth/apple.provider.ts +266 -0
- package/backend/src/providers/oauth/base.provider.ts +29 -0
- package/backend/src/providers/oauth/discord.provider.ts +195 -0
- package/backend/src/providers/oauth/facebook.provider.ts +194 -0
- package/backend/src/providers/oauth/github.provider.ts +208 -0
- package/backend/src/providers/oauth/google.provider.ts +249 -0
- package/backend/src/providers/oauth/index.ts +8 -0
- package/backend/src/providers/oauth/linkedin.provider.ts +240 -0
- package/backend/src/providers/oauth/microsoft.provider.ts +169 -0
- package/backend/src/providers/oauth/x.provider.ts +202 -0
- package/backend/src/providers/storage/base.provider.ts +29 -0
- package/backend/src/providers/storage/local.provider.ts +103 -0
- package/backend/src/providers/storage/s3.provider.ts +313 -0
- package/backend/src/server.ts +317 -288
- package/backend/src/{core/ai/config.ts → services/ai/ai-config.service.ts} +19 -24
- package/backend/src/services/ai/ai-model.service.ts +60 -0
- package/backend/src/{core/ai/usage.ts → services/ai/ai-usage.service.ts} +28 -35
- package/backend/src/{core/ai/chat.ts → services/ai/chat-completion.service.ts} +37 -24
- package/backend/src/services/ai/helpers.ts +64 -0
- package/backend/src/{core/ai/image.ts → services/ai/image-generation.service.ts} +17 -19
- package/backend/src/services/ai/index.ts +13 -0
- package/backend/src/services/auth/auth-config.service.ts +250 -0
- package/backend/src/services/auth/auth-otp.service.ts +424 -0
- package/backend/src/services/auth/auth.service.ts +1150 -0
- package/backend/src/services/auth/index.ts +4 -0
- package/backend/src/{core/auth/oauth.ts → services/auth/oauth-config.service.ts} +106 -52
- package/backend/src/{core/database/advance.ts → services/database/database-advance.service.ts} +97 -131
- package/backend/src/services/database/database-table.service.ts +802 -0
- package/backend/src/services/database/database.service.ts +127 -0
- package/backend/src/services/email/email.service.ts +73 -0
- package/backend/src/{core/functions/functions.ts → services/functions/function.service.ts} +95 -88
- package/backend/src/{core/logs/audit.ts → services/logs/audit.service.ts} +92 -75
- package/backend/src/services/logs/log.service.ts +73 -0
- package/backend/src/services/realtime/index.ts +3 -0
- package/backend/src/services/realtime/realtime-auth.service.ts +104 -0
- package/backend/src/services/realtime/realtime-channel.service.ts +237 -0
- package/backend/src/services/realtime/realtime-message.service.ts +260 -0
- package/backend/src/{core/secrets/secrets.ts → services/secrets/secret.service.ts} +48 -66
- package/backend/src/services/storage/storage.service.ts +617 -0
- package/backend/src/services/usage/usage.service.ts +149 -0
- package/backend/src/types/auth.ts +77 -2
- package/backend/src/types/email.ts +8 -0
- package/backend/src/types/error-constants.ts +4 -0
- package/backend/src/types/logs.ts +0 -29
- package/backend/src/types/realtime.ts +18 -0
- package/backend/src/{core/socket/types.ts → types/socket.ts} +11 -36
- package/backend/src/utils/cookies.ts +35 -0
- package/backend/src/utils/environment.ts +9 -3
- package/backend/src/utils/logger.ts +20 -2
- package/backend/src/utils/s3-config-loader.ts +64 -0
- package/backend/src/utils/seed.ts +301 -205
- package/backend/src/utils/sql-parser.ts +91 -1
- package/backend/src/utils/utils.ts +114 -0
- package/backend/src/utils/validations.ts +40 -4
- package/backend/tests/README.md +133 -133
- package/backend/tests/cleanup-all-test-data.sh +230 -230
- package/backend/tests/cloud/test-s3-multitenant.sh +131 -131
- package/backend/tests/local/comprehensive-curl-tests.sh +155 -155
- package/backend/tests/local/test-ai-config.sh +129 -0
- package/backend/tests/local/test-ai-usage.sh +80 -0
- package/backend/tests/local/test-auth-router.sh +143 -143
- package/backend/tests/local/test-database-router.sh +222 -222
- package/backend/tests/local/test-e2e.sh +240 -240
- package/backend/tests/local/test-fk-errors.sh +96 -96
- package/backend/tests/local/test-functions.sh +123 -0
- package/backend/tests/local/test-id-field.sh +200 -200
- package/backend/tests/local/test-logs.sh +132 -0
- package/backend/tests/local/test-public-bucket.sh +264 -264
- package/backend/tests/local/test-secrets.sh +249 -247
- package/backend/tests/local/test-serverless-functions.sh.disabled +325 -325
- package/backend/tests/local/test-traditional-rest.sh +208 -208
- package/backend/tests/manual/README.md +50 -50
- package/backend/tests/manual/create-large-table-simple.sql +10 -10
- package/backend/tests/manual/seed-large-table.sql +100 -100
- package/backend/tests/manual/setup-large-table-extras.sql +33 -33
- package/backend/tests/manual/test-bulk-upsert.sh +409 -409
- package/backend/tests/manual/test-database-advance.sh +296 -296
- package/backend/tests/manual/test-postgrest-stability.sh +191 -191
- package/backend/tests/manual/test-rawsql-export-import.sh +411 -411
- package/backend/tests/manual/test-rawsql-modes.sh +244 -0
- package/backend/tests/manual/test-universal-storage.sh +263 -263
- package/backend/tests/manual/test-users.sql +17 -17
- package/backend/tests/run-all-tests.sh +139 -139
- package/backend/tests/setup.ts +0 -0
- package/backend/tests/test-config.sh +338 -302
- package/backend/tests/unit/analyze-query.test.ts +697 -0
- package/backend/tests/unit/cloud-token.test.ts +48 -0
- package/backend/tests/unit/constant.test.ts +8 -0
- package/backend/tests/unit/email.test.ts +372 -0
- package/backend/tests/unit/environment.test.ts +59 -0
- package/backend/tests/unit/helpers.test.ts +63 -0
- package/backend/tests/unit/logger.test.ts +22 -0
- package/backend/tests/unit/rate-limit.test.ts +154 -0
- package/backend/tests/unit/response.test.ts +58 -0
- package/backend/tests/unit/sql-parser.test.ts +74 -0
- package/backend/tests/unit/uuid.test.ts +21 -0
- package/backend/tests/unit/validations.test.ts +80 -0
- package/backend/tsconfig.json +22 -22
- package/backend/vitest.config.ts +11 -0
- package/claude-plugin/.claude-plugin/plugin.json +24 -0
- package/claude-plugin/README.md +133 -0
- package/claude-plugin/skills/insforge-schema-patterns/SKILL.md +270 -0
- package/docker-compose.prod.yml +204 -144
- package/docker-compose.yml +232 -167
- package/docker-init/db/db-init.sql +97 -125
- package/docker-init/db/jwt.sql +5 -5
- package/docker-init/db/postgresql.conf +16 -16
- package/docker-init/logs/vector.yml +236 -0
- package/docs/README.md +44 -0
- package/docs/agent-docs/real-time.md +269 -0
- package/docs/changelog.mdx +119 -0
- package/docs/core-concepts/ai/architecture.mdx +373 -0
- package/docs/core-concepts/ai/sdk.mdx +213 -0
- package/docs/core-concepts/authentication/architecture.mdx +278 -0
- package/docs/core-concepts/authentication/sdk.mdx +414 -0
- package/docs/core-concepts/authentication/ui-components/customization.mdx +529 -0
- package/docs/core-concepts/authentication/ui-components/nextjs.mdx +221 -0
- package/docs/core-concepts/authentication/ui-components/react-router.mdx +184 -0
- package/docs/core-concepts/authentication/ui-components/react.mdx +129 -0
- package/docs/core-concepts/database/architecture.mdx +256 -0
- package/docs/core-concepts/database/sdk.mdx +382 -0
- package/docs/core-concepts/email/architecture.mdx +101 -0
- package/docs/core-concepts/email/sdk.mdx +53 -0
- package/docs/core-concepts/functions/architecture.mdx +105 -0
- package/docs/core-concepts/functions/sdk.mdx +184 -0
- package/docs/core-concepts/realtime/architecture.mdx +446 -0
- package/docs/core-concepts/realtime/sdk.mdx +409 -0
- package/docs/core-concepts/storage/architecture.mdx +243 -0
- package/docs/core-concepts/storage/sdk.mdx +253 -0
- package/docs/deployment/README.md +94 -0
- package/docs/deployment/deploy-to-aws-ec2.md +565 -0
- package/docs/deployment/deploy-to-azure-virtual-machines.md +313 -0
- package/docs/deployment/deploy-to-google-cloud-compute-engine.md +613 -0
- package/docs/deployment/deploy-to-render.md +441 -0
- package/docs/deprecated/insforge-auth-api.md +214 -214
- package/docs/deprecated/insforge-auth-sdk.md +99 -99
- package/docs/deprecated/insforge-db-api.md +358 -358
- package/docs/deprecated/insforge-db-sdk.md +139 -139
- package/docs/deprecated/insforge-debug-sdk.md +156 -156
- package/docs/deprecated/insforge-debug.md +64 -64
- package/docs/deprecated/insforge-instructions.md +123 -123
- package/docs/deprecated/insforge-project.md +117 -117
- package/docs/deprecated/insforge-storage-api.md +278 -278
- package/docs/deprecated/insforge-storage-sdk.md +158 -158
- package/docs/docs.json +232 -0
- package/docs/examples/framework-guides/nextjs.mdx +131 -0
- package/docs/examples/framework-guides/nuxt.mdx +165 -0
- package/docs/examples/framework-guides/react.mdx +165 -0
- package/docs/examples/framework-guides/svelte.mdx +153 -0
- package/docs/examples/framework-guides/vue.mdx +159 -0
- package/docs/examples/overview.mdx +67 -0
- package/docs/favicon.svg +19 -0
- package/docs/images/changelog/dec-2025/ai-integration.png +0 -0
- package/docs/images/changelog/dec-2025/ai-models.webp +0 -0
- package/docs/images/changelog/dec-2025/alipay-payment.webp +0 -0
- package/docs/images/changelog/dec-2025/apple-login.jpg +0 -0
- package/docs/images/changelog/dec-2025/mcp-installer.png +0 -0
- package/docs/images/changelog/dec-2025/realtime-module.jpg +0 -0
- package/docs/images/changelog/nov-2025/auth-components.webp +0 -0
- package/docs/images/changelog/nov-2025/database-metadata.webp +0 -0
- package/docs/images/changelog/nov-2025/quickstart-prompts.webp +0 -0
- package/docs/images/changelog/nov-2025/sql-editor.webp +0 -0
- package/docs/images/changelog/nov-2025/usage-page.webp +0 -0
- package/docs/images/changelog/october-2025/csv-upload.webp +0 -0
- package/docs/images/changelog/october-2025/logs-feature.webp +0 -0
- package/docs/images/changelog/october-2025/oauth-providers.webp +0 -0
- package/docs/images/checks-passed.png +0 -0
- package/docs/images/dashboard-connect-expanded.png +0 -0
- package/docs/images/dashboard-connect.png +0 -0
- package/docs/images/hero-dark.png +0 -0
- package/docs/images/hero-light.png +0 -0
- package/docs/images/icons/ai.svg +4 -0
- package/docs/images/icons/auth.svg +1 -0
- package/docs/images/icons/database.svg +1 -0
- package/docs/images/icons/function.svg +1 -0
- package/docs/images/icons/storage.svg +1 -0
- package/docs/images/logos/nextjs.svg +4 -0
- package/docs/images/logos/nuxt.svg +4 -0
- package/docs/images/logos/react.svg +5 -0
- package/docs/images/logos/svelte.svg +4 -0
- package/docs/images/logos/vue.svg +5 -0
- package/docs/images/mcp-install.png +0 -0
- package/docs/images/onboarding-mcp.png +0 -0
- package/docs/insforge-instructions-sdk.md +89 -407
- package/docs/introduction.mdx +45 -0
- package/docs/logo/dark.svg +22 -0
- package/docs/logo/light.svg +20 -0
- package/docs/partnership.mdx +652 -0
- package/docs/quickstart.mdx +83 -0
- package/docs/showcase/2048-arena.png +0 -0
- package/docs/showcase/framegen-cloud.png +0 -0
- package/docs/showcase/line-connect-race.png +0 -0
- package/docs/showcase/moment-vibe.png +0 -0
- package/docs/showcase/national-flags.png +0 -0
- package/docs/showcase/pokemon-vibe.png +0 -0
- package/docs/showcase/pure-browse-buy.png +0 -0
- package/docs/showcase.mdx +52 -0
- package/docs/snippets/sdk-installation.mdx +22 -0
- package/docs/snippets/service-icons.mdx +27 -0
- package/eslint.config.js +10 -3
- package/examples/oauth/frontend-oauth-example.html +250 -250
- package/examples/response-examples.md +443 -443
- package/frontend/components.json +17 -17
- package/frontend/package.json +69 -63
- package/frontend/src/App.tsx +13 -82
- package/frontend/src/assets/icons/checkbox_checked.svg +6 -6
- package/frontend/src/assets/icons/checkbox_undetermined.svg +6 -6
- package/frontend/src/assets/icons/checked.svg +3 -3
- package/frontend/src/assets/icons/connected.svg +3 -0
- package/frontend/src/assets/icons/error.svg +3 -3
- package/frontend/src/assets/icons/loader.svg +9 -0
- package/frontend/src/assets/icons/pencil.svg +4 -4
- package/frontend/src/assets/icons/refresh.svg +4 -4
- package/frontend/src/assets/icons/step_active.svg +3 -3
- package/frontend/src/assets/icons/step_inactive.svg +11 -11
- package/frontend/src/assets/icons/warning.svg +3 -3
- package/frontend/src/assets/logos/apple.svg +4 -0
- package/frontend/src/assets/logos/claude_code.svg +3 -3
- package/frontend/src/assets/logos/cline.svg +6 -6
- package/frontend/src/assets/logos/cursor.svg +20 -20
- package/frontend/src/assets/logos/discord.svg +8 -8
- package/frontend/src/assets/logos/facebook.svg +3 -0
- package/frontend/src/assets/logos/gemini.svg +19 -19
- package/frontend/src/assets/logos/github.svg +5 -5
- package/frontend/src/assets/logos/google.svg +13 -13
- package/frontend/src/assets/logos/grok.svg +10 -10
- package/frontend/src/assets/logos/insforge_dark.svg +15 -15
- package/frontend/src/assets/logos/insforge_light.svg +15 -15
- package/frontend/src/assets/logos/instagram.svg +2 -0
- package/frontend/src/assets/logos/linkedin.svg +3 -0
- package/frontend/src/assets/logos/microsoft.svg +1 -0
- package/frontend/src/assets/logos/openai.svg +10 -10
- package/frontend/src/assets/logos/roo_code.svg +9 -9
- package/frontend/src/assets/logos/spotify.svg +17 -0
- package/frontend/src/assets/logos/tiktok.svg +6 -0
- package/frontend/src/assets/logos/trae.svg +3 -3
- package/frontend/src/assets/logos/windsurf.svg +10 -10
- package/frontend/src/assets/logos/x.svg +3 -0
- package/frontend/src/components/Checkbox.tsx +27 -29
- package/frontend/src/components/CodeBlock.tsx +55 -2
- package/frontend/src/components/CodeEditor.tsx +92 -0
- package/frontend/src/components/ConfirmDialog.tsx +1 -1
- package/frontend/src/components/ConnectCTA.tsx +38 -0
- package/frontend/src/components/CopyButton.tsx +52 -15
- package/frontend/src/components/ErrorState.tsx +1 -2
- package/frontend/src/components/FeatureSidebar.tsx +6 -6
- package/frontend/src/components/FeatureSidebarItem.tsx +2 -2
- package/frontend/src/components/JsonHighlight.tsx +21 -9
- package/frontend/src/components/ProjectInfoModal.tsx +128 -0
- package/frontend/src/components/PromptDialog.tsx +1 -4
- package/frontend/src/components/SearchInput.tsx +1 -2
- package/frontend/src/components/Stepper.tsx +53 -0
- package/frontend/src/components/ThemeToggle.tsx +3 -3
- package/frontend/src/components/datagrid/DataGrid.tsx +25 -32
- package/frontend/src/components/datagrid/cell-editors/DateCellEditor.tsx +1 -2
- package/frontend/src/components/datagrid/cell-editors/JsonCellEditor.tsx +2 -4
- package/frontend/src/components/datagrid/index.ts +23 -0
- package/frontend/src/components/index.ts +23 -30
- package/frontend/src/components/layout/AppHeader.tsx +131 -91
- package/frontend/src/components/layout/AppSidebar.tsx +80 -170
- package/frontend/src/components/layout/Layout.tsx +12 -23
- package/frontend/src/components/layout/PrimaryMenu.tsx +187 -0
- package/frontend/src/components/layout/SecondaryMenu.tsx +70 -0
- package/frontend/src/components/layout/index.ts +5 -0
- package/frontend/src/components/radix/Tooltip.tsx +24 -13
- package/frontend/src/components/radix/index.ts +22 -0
- package/frontend/src/features/ai/components/AIConfigCard.tsx +129 -83
- package/frontend/src/features/ai/components/AIEmptyState.tsx +12 -7
- package/frontend/src/features/ai/components/ModalityFilterSidebar.tsx +101 -0
- package/frontend/src/features/ai/components/ModelSelectionDialog.tsx +135 -0
- package/frontend/src/features/ai/components/ModelSelectionGrid.tsx +51 -0
- package/frontend/src/features/ai/components/SystemPromptDialog.tsx +118 -0
- package/frontend/src/features/ai/components/index.ts +6 -0
- package/frontend/src/features/ai/helpers.ts +57 -71
- package/frontend/src/features/ai/hooks/useAIConfigs.ts +39 -113
- package/frontend/src/features/ai/hooks/useAIUsage.ts +0 -2
- package/frontend/src/features/ai/pages/AIPage.tsx +166 -0
- package/frontend/src/features/ai/services/ai.service.ts +5 -5
- package/frontend/src/features/auth/components/AuthPreview.tsx +96 -0
- package/frontend/src/features/auth/components/OAuthConfigDialog.tsx +54 -30
- package/frontend/src/features/auth/components/UserFormDialog.tsx +13 -6
- package/frontend/src/features/auth/components/UsersDataGrid.tsx +50 -14
- package/frontend/src/features/auth/components/index.ts +5 -0
- package/frontend/src/features/auth/helpers.tsx +208 -0
- package/frontend/src/features/auth/hooks/useAnonToken.ts +30 -0
- package/frontend/src/features/auth/hooks/useAuthConfig.ts +48 -0
- package/frontend/src/features/auth/hooks/useOAuthConfig.ts +14 -10
- package/frontend/src/features/auth/hooks/useUsers.ts +43 -5
- package/frontend/src/features/auth/index.ts +3 -2
- package/frontend/src/features/auth/pages/AuthMethodsPage.tsx +275 -0
- package/frontend/src/features/auth/pages/ConfigurationPage.tsx +395 -0
- package/frontend/src/features/auth/pages/UsersPage.tsx +257 -0
- package/frontend/src/features/auth/services/anonToken.service.ts +11 -0
- package/frontend/src/features/auth/services/config.service.ts +19 -0
- package/frontend/src/features/auth/services/{oauth.service.ts → oauth-config.service.ts} +4 -4
- package/frontend/src/features/auth/services/{auth.service.ts → user.service.ts} +7 -53
- package/frontend/src/features/dashboard/components/ConnectionSuccessBanner.tsx +35 -0
- package/frontend/src/features/dashboard/components/PromptCard.tsx +21 -0
- package/frontend/src/features/dashboard/components/PromptDialog.tsx +103 -0
- package/frontend/src/features/dashboard/components/StatsCard.tsx +50 -0
- package/frontend/src/features/dashboard/components/index.ts +4 -0
- package/frontend/src/features/dashboard/pages/DashboardPage.tsx +212 -0
- package/frontend/src/features/dashboard/prompts/ai-chatbot.ts +13 -0
- package/frontend/src/features/dashboard/prompts/crm-system.ts +13 -0
- package/frontend/src/features/dashboard/prompts/ecommerce-platform.ts +12 -0
- package/frontend/src/features/dashboard/prompts/index.ts +31 -0
- package/frontend/src/features/dashboard/prompts/instagram-clone.ts +11 -0
- package/frontend/src/features/dashboard/prompts/notion-clone.ts +14 -0
- package/frontend/src/features/dashboard/prompts/reddit-clone.ts +12 -0
- package/frontend/src/features/database/components/DatabaseDataGrid.tsx +48 -17
- package/frontend/src/features/database/components/ForeignKeyCell.tsx +15 -34
- package/frontend/src/features/database/components/ForeignKeyPopover.tsx +19 -20
- package/frontend/src/features/database/components/LinkRecordModal.tsx +120 -125
- package/frontend/src/features/database/components/RecordFormDialog.tsx +22 -33
- package/frontend/src/features/database/components/RecordFormField.tsx +45 -47
- package/frontend/src/features/database/components/SQLModal.tsx +75 -0
- package/frontend/src/features/database/components/TableEmptyState.tsx +6 -5
- package/frontend/src/features/database/components/TableForm.tsx +28 -19
- package/frontend/src/features/database/components/TableFormColumn.tsx +2 -3
- package/frontend/src/features/database/components/TableSidebar.tsx +1 -1
- package/frontend/src/features/database/components/TablesEmptyState.tsx +48 -0
- package/frontend/src/features/database/components/TemplateCard.tsx +37 -0
- package/frontend/src/features/database/components/TemplatePreview.tsx +92 -0
- package/frontend/src/features/database/components/index.ts +19 -0
- package/frontend/src/features/database/constants.ts +28 -2
- package/frontend/src/features/database/contexts/SQLEditorContext.tsx +188 -0
- package/frontend/src/features/database/helpers.ts +2 -2
- package/frontend/src/features/database/hooks/useCSVImport.ts +29 -0
- package/frontend/src/features/database/hooks/useDatabase.ts +66 -0
- package/frontend/src/features/database/hooks/useRawSQL.ts +55 -0
- package/frontend/src/features/database/hooks/useRecords.ts +139 -0
- package/frontend/src/features/database/hooks/useTables.ts +135 -0
- package/frontend/src/features/database/index.ts +7 -1
- package/frontend/src/features/database/pages/FunctionsPage.tsx +203 -0
- package/frontend/src/features/database/pages/IndexesPage.tsx +228 -0
- package/frontend/src/features/database/pages/PoliciesPage.tsx +237 -0
- package/frontend/src/features/database/pages/SQLEditorPage.tsx +382 -0
- package/frontend/src/features/database/{page/DatabasePage.tsx → pages/TablesPage.tsx} +168 -209
- package/frontend/src/features/database/pages/TemplatesPage.tsx +39 -0
- package/frontend/src/features/database/pages/TriggersPage.tsx +230 -0
- package/frontend/src/features/database/services/advance.service.ts +40 -0
- package/frontend/src/features/database/services/database.service.ts +33 -194
- package/frontend/src/features/database/services/record.service.ts +219 -0
- package/frontend/src/features/database/services/table.service.ts +58 -0
- package/frontend/src/features/database/templates/ai-chatbot.ts +402 -0
- package/frontend/src/features/database/templates/crm-system.ts +528 -0
- package/frontend/src/features/database/templates/ecommerce-platform.ts +553 -0
- package/frontend/src/features/database/templates/index.ts +34 -0
- package/frontend/src/features/database/templates/instagram-clone.ts +222 -0
- package/frontend/src/features/database/templates/notion-clone.ts +483 -0
- package/frontend/src/features/database/templates/reddit-clone.ts +526 -0
- package/frontend/src/features/functions/components/FunctionRow.tsx +2 -1
- package/frontend/src/features/functions/components/FunctionsSidebar.tsx +1 -1
- package/frontend/src/features/functions/components/SecretRow.tsx +1 -1
- package/frontend/src/features/functions/components/index.ts +5 -0
- package/frontend/src/features/functions/hooks/useFunctions.ts +4 -4
- package/frontend/src/features/{secrets → functions}/hooks/useSecrets.ts +5 -5
- package/frontend/src/features/functions/pages/FunctionsPage.tsx +148 -0
- package/frontend/src/features/functions/{components/SecretsContent.tsx → pages/SecretsPage.tsx} +19 -21
- package/frontend/src/features/functions/services/{functions.service.ts → function.service.ts} +2 -2
- package/frontend/src/features/{secrets/services/secrets.service.ts → functions/services/secret.service.ts} +2 -2
- package/frontend/src/features/login/hooks/usePartnerOrigin.ts +27 -0
- package/frontend/src/features/login/pages/CloudLoginPage.tsx +118 -0
- package/frontend/src/features/login/{page → pages}/LoginPage.tsx +16 -23
- package/frontend/src/features/login/services/partnership.service.ts +65 -0
- package/frontend/src/features/logs/components/LogsDataGrid.tsx +89 -0
- package/frontend/src/features/logs/components/SeverityBadge.tsx +18 -0
- package/frontend/src/features/logs/components/index.ts +2 -0
- package/frontend/src/features/logs/helpers.ts +24 -0
- package/frontend/src/features/logs/hooks/useAuditLogs.ts +4 -4
- package/frontend/src/features/logs/hooks/useLogSources.ts +137 -0
- package/frontend/src/features/logs/hooks/useLogs.ts +163 -0
- package/frontend/src/features/logs/hooks/useMcpUsage.ts +128 -0
- package/frontend/src/features/logs/index.ts +8 -2
- package/frontend/src/features/logs/{page → pages}/AuditsPage.tsx +91 -38
- package/frontend/src/features/logs/pages/LogsPage.tsx +152 -0
- package/frontend/src/features/logs/pages/MCPLogsPage.tsx +84 -0
- package/frontend/src/features/logs/services/audit.service.ts +63 -0
- package/frontend/src/features/logs/services/log.service.ts +15 -110
- package/frontend/src/features/logs/services/usage.service.ts +31 -0
- package/frontend/src/features/onboard/components/McpConnectionStatus.tsx +68 -0
- package/frontend/src/features/onboard/components/OnboardingModal.tsx +267 -0
- package/frontend/src/features/onboard/components/VideoDemoModal.tsx +38 -0
- package/frontend/src/features/onboard/components/index.ts +4 -0
- package/frontend/src/features/onboard/components/mcp/CursorDeeplinkGenerator.tsx +2 -2
- package/frontend/src/features/onboard/components/mcp/{mcp-helper.tsx → helpers.tsx} +8 -8
- package/frontend/src/features/onboard/components/mcp/index.ts +2 -3
- package/frontend/src/features/onboard/index.ts +13 -3
- package/frontend/src/features/realtime/components/ChannelRow.tsx +83 -0
- package/frontend/src/features/realtime/components/EditChannelModal.tsx +246 -0
- package/frontend/src/features/realtime/components/MessageRow.tsx +85 -0
- package/frontend/src/features/realtime/components/RealtimeEmptyState.tsx +30 -0
- package/frontend/src/features/realtime/hooks/useRealtime.ts +218 -0
- package/frontend/src/features/realtime/index.ts +11 -0
- package/frontend/src/features/realtime/pages/RealtimeChannelsPage.tsx +172 -0
- package/frontend/src/features/realtime/pages/RealtimeMessagesPage.tsx +211 -0
- package/frontend/src/features/realtime/pages/RealtimePermissionsPage.tsx +191 -0
- package/frontend/src/features/realtime/services/realtime.service.ts +107 -0
- package/frontend/src/features/storage/components/BucketEmptyState.tsx +9 -6
- package/frontend/src/features/storage/components/BucketFormDialog.tsx +25 -41
- package/frontend/src/features/storage/components/FilePreviewDialog.tsx +20 -8
- package/frontend/src/features/storage/components/StorageDataGrid.tsx +4 -3
- package/frontend/src/features/storage/components/StorageManager.tsx +23 -34
- package/frontend/src/features/storage/components/index.ts +12 -0
- package/frontend/src/features/storage/hooks/useStorage.ts +208 -0
- package/frontend/src/features/storage/{page → pages}/StoragePage.tsx +41 -143
- package/frontend/src/features/storage/services/storage.service.ts +22 -1
- package/frontend/src/features/visualizer/components/AuthNode.tsx +72 -56
- package/frontend/src/features/visualizer/components/BucketNode.tsx +4 -4
- package/frontend/src/features/visualizer/components/SchemaVisualizer.tsx +108 -80
- package/frontend/src/features/visualizer/components/TableNode.tsx +34 -41
- package/frontend/src/features/visualizer/components/VisualizerSkeleton.tsx +12 -4
- package/frontend/src/features/visualizer/pages/VisualizerPage.tsx +97 -0
- package/frontend/src/index.css +1 -0
- package/frontend/src/lib/analytics/posthog.tsx +27 -0
- package/frontend/src/lib/contexts/AuthContext.tsx +38 -31
- package/frontend/src/lib/contexts/SocketContext.tsx +123 -80
- package/frontend/src/{features/metadata → lib}/hooks/useMetadata.ts +1 -1
- package/frontend/src/lib/hooks/useToast.tsx +6 -2
- package/frontend/src/lib/routing/AppRoutes.tsx +99 -0
- package/frontend/src/lib/routing/RequireAuth.tsx +27 -0
- package/frontend/src/lib/utils/cloudMessaging.ts +20 -0
- package/frontend/src/lib/utils/menuItems.ts +207 -0
- package/frontend/src/lib/utils/{validation-schemas.ts → schemaValidations.ts} +10 -5
- package/frontend/src/lib/utils/utils.ts +32 -1
- package/frontend/src/vite-env.d.ts +1 -0
- package/frontend/tsconfig.json +25 -25
- package/frontend/tsconfig.node.json +9 -9
- package/frontend/vite.config.ts +5 -3
- package/functions/deno.json +24 -24
- package/functions/server.ts +315 -290
- package/functions/worker-template.js +15 -4
- package/i18n/README.ar.md +130 -0
- package/i18n/README.de.md +130 -0
- package/i18n/README.es.md +154 -0
- package/i18n/README.fr.md +134 -0
- package/i18n/README.hi.md +129 -0
- package/i18n/README.ja.md +174 -0
- package/i18n/README.ko.md +137 -0
- package/i18n/README.pt-BR.md +131 -0
- package/i18n/README.ru.md +129 -0
- package/i18n/README.zh-CN.md +133 -0
- package/openapi/ai.yaml +715 -688
- package/openapi/auth.yaml +1244 -563
- package/openapi/email.yaml +158 -0
- package/openapi/functions.yaml +475 -475
- package/openapi/health.yaml +29 -29
- package/openapi/logs.yaml +223 -223
- package/openapi/metadata.yaml +177 -177
- package/openapi/realtime.yaml +699 -0
- package/openapi/records.yaml +381 -381
- package/openapi/secrets.yaml +370 -370
- package/openapi/storage.yaml +875 -875
- package/openapi/tables.yaml +463 -463
- package/package.json +97 -88
- package/shared-schemas/package.json +31 -31
- package/shared-schemas/src/ai-api.schema.ts +34 -58
- package/shared-schemas/src/ai.schema.ts +63 -54
- package/shared-schemas/src/auth-api.schema.ts +352 -193
- package/shared-schemas/src/auth.schema.ts +43 -7
- package/shared-schemas/src/cloud-events.schema.ts +57 -0
- package/shared-schemas/src/database-api.schema.ts +35 -4
- package/shared-schemas/src/database.schema.ts +40 -1
- package/shared-schemas/src/docs.schema.ts +26 -0
- package/shared-schemas/src/email-api.schema.ts +30 -0
- package/shared-schemas/src/index.ts +5 -0
- package/shared-schemas/src/logs-api.schema.ts +7 -1
- package/shared-schemas/src/logs.schema.ts +26 -0
- package/shared-schemas/src/metadata.schema.ts +18 -4
- package/shared-schemas/src/realtime-api.schema.ts +111 -0
- package/shared-schemas/src/realtime.schema.ts +143 -0
- package/shared-schemas/tsconfig.json +21 -21
- package/tsconfig.json +7 -7
- package/zeabur/README.md +13 -0
- package/zeabur/template.yml +1032 -0
- package/.github/workflows/deploy-aws.yml +0 -130
- package/backend/src/api/routes/agent.ts +0 -29
- package/backend/src/api/routes/auth.oauth.ts +0 -482
- package/backend/src/api/routes/auth.ts +0 -386
- package/backend/src/api/routes/docs.ts +0 -66
- package/backend/src/api/routes/functions.ts +0 -183
- package/backend/src/api/routes/openapi.ts +0 -82
- package/backend/src/api/routes/usage.ts +0 -96
- package/backend/src/core/ai/client.ts +0 -242
- package/backend/src/core/ai/model.ts +0 -117
- package/backend/src/core/auth/auth.ts +0 -780
- package/backend/src/core/database/manager.ts +0 -178
- package/backend/src/core/database/table.ts +0 -772
- package/backend/src/core/documentation/agent.ts +0 -689
- package/backend/src/core/documentation/openapi.ts +0 -856
- package/backend/src/core/logs/analytics.ts +0 -76
- package/backend/src/core/logs/providers/localdb.provider.ts +0 -246
- package/backend/src/core/socket/socket.ts +0 -388
- package/backend/src/core/storage/storage.ts +0 -923
- package/backend/src/utils/cloud-token.ts +0 -39
- package/backend/src/utils/helpers.ts +0 -49
- package/backend/src/utils/uuid.ts +0 -9
- package/backend/tests/manual/test-better-auth.sh +0 -303
- package/docker-init/db/logs.sql +0 -9
- package/frontend/README.md +0 -112
- package/frontend/src/components/datagrid/index.tsx +0 -20
- package/frontend/src/components/layout/CloudLayout.tsx +0 -95
- package/frontend/src/features/ai/components/AIConfigDialog.tsx +0 -76
- package/frontend/src/features/ai/components/AIConfigForm.tsx +0 -222
- package/frontend/src/features/ai/components/fields/ModalityField.tsx +0 -87
- package/frontend/src/features/ai/components/fields/ModelSelectionField.tsx +0 -134
- package/frontend/src/features/ai/components/fields/SystemPromptField.tsx +0 -33
- package/frontend/src/features/ai/page/AIPage.tsx +0 -178
- package/frontend/src/features/auth/components/AddOAuthDialog.tsx +0 -106
- package/frontend/src/features/auth/components/AuthMethodTab.tsx +0 -238
- package/frontend/src/features/auth/components/UsersTab.tsx +0 -114
- package/frontend/src/features/auth/page/AuthenticationPage.tsx +0 -169
- package/frontend/src/features/dashboard/page/DashboardPage.tsx +0 -194
- package/frontend/src/features/database/hooks/UseLinkModal.tsx +0 -78
- package/frontend/src/features/functions/components/FunctionViewer.tsx +0 -46
- package/frontend/src/features/functions/components/FunctionsContent.tsx +0 -88
- package/frontend/src/features/functions/page/FunctionsPage.tsx +0 -28
- package/frontend/src/features/login/components/AuthErrorBoundary.tsx +0 -87
- package/frontend/src/features/login/components/PrivateRoute.tsx +0 -24
- package/frontend/src/features/login/page/CloudLoginPage.tsx +0 -93
- package/frontend/src/features/logs/components/AnalyticsLogsTable.tsx +0 -313
- package/frontend/src/features/logs/components/LogsTable.tsx +0 -199
- package/frontend/src/features/logs/page/AnalyticsLogsPage.tsx +0 -530
- package/frontend/src/features/metadata/index.ts +0 -0
- package/frontend/src/features/metadata/page/MetadataPage.tsx +0 -136
- package/frontend/src/features/onboard/components/CompletionCard.tsx +0 -41
- package/frontend/src/features/onboard/components/OnboardButton.tsx +0 -84
- package/frontend/src/features/onboard/components/StepContent.tsx +0 -91
- package/frontend/src/features/onboard/components/TestConnectionStep.tsx +0 -53
- package/frontend/src/features/onboard/components/mcp/McpInstallation.tsx +0 -144
- package/frontend/src/features/onboard/page/OnBoardPage.tsx +0 -104
- package/frontend/src/features/onboard/types.ts +0 -8
- package/frontend/src/features/visualizer/page/VisualizerPage.tsx +0 -127
- package/frontend/src/lib/contexts/OnboardStepContext.tsx +0 -68
- package/frontend/src/lib/hooks/useOnboardingCompletion.ts +0 -29
- /package/backend/src/api/{middleware → middlewares}/error.ts +0 -0
- /package/backend/src/api/{middleware → middlewares}/upload.ts +0 -0
- /package/frontend/src/{features/metadata → lib}/services/metadata.service.ts +0 -0
|
@@ -0,0 +1,446 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: Architecture
|
|
3
|
+
description: Real-time messaging with PostgreSQL triggers, WebSockets, and webhooks
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
## Overview
|
|
7
|
+
|
|
8
|
+
InsForge Realtime provides a powerful event-driven messaging system that bridges database changes to connected clients. Events are triggered by PostgreSQL triggers, delivered through WebSocket connections via Socket.IO, and optionally forwarded to webhook endpoints.
|
|
9
|
+
|
|
10
|
+
## Technology Stack
|
|
11
|
+
|
|
12
|
+
```mermaid
|
|
13
|
+
graph TB
|
|
14
|
+
Trigger[Database Trigger] --> Publish[realtime.publish]
|
|
15
|
+
Publish --> Messages[(realtime.messages)]
|
|
16
|
+
Messages --> PGNotify[pg_notify]
|
|
17
|
+
PGNotify --> Manager[Realtime Manager]
|
|
18
|
+
Manager --> SocketIO[Socket.IO Server]
|
|
19
|
+
Manager --> Webhooks[Webhook Sender]
|
|
20
|
+
SocketIO --> SDK[InsForge SDK]
|
|
21
|
+
SDK --> App[Client Application]
|
|
22
|
+
Webhooks --> External[External Services]
|
|
23
|
+
|
|
24
|
+
Channels[(realtime.channels)]
|
|
25
|
+
RLS[RLS Policies]
|
|
26
|
+
RLS -.->|SELECT| Channels
|
|
27
|
+
RLS -.->|INSERT| Messages
|
|
28
|
+
|
|
29
|
+
style Trigger fill:#4c1d95,stroke:#8b5cf6,color:#ede9fe
|
|
30
|
+
style Publish fill:#4c1d95,stroke:#8b5cf6,color:#ede9fe
|
|
31
|
+
style Messages fill:#0e7490,stroke:#06b6d4,color:#cffafe
|
|
32
|
+
style Channels fill:#0e7490,stroke:#06b6d4,color:#cffafe
|
|
33
|
+
style PGNotify fill:#0e7490,stroke:#06b6d4,color:#cffafe
|
|
34
|
+
style RLS fill:#7c2d12,stroke:#f97316,color:#fed7aa
|
|
35
|
+
style Manager fill:#166534,stroke:#22c55e,color:#dcfce7
|
|
36
|
+
style SocketIO fill:#c2410c,stroke:#fb923c,color:#fed7aa
|
|
37
|
+
style Webhooks fill:#c2410c,stroke:#fb923c,color:#fed7aa
|
|
38
|
+
style SDK fill:#1e40af,stroke:#3b82f6,color:#dbeafe
|
|
39
|
+
style App fill:#1e293b,stroke:#475569,color:#e2e8f0
|
|
40
|
+
style External fill:#1e293b,stroke:#475569,color:#e2e8f0
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Core Components
|
|
44
|
+
|
|
45
|
+
| Component | Technology | Purpose |
|
|
46
|
+
|-----------|------------|---------|
|
|
47
|
+
| **Realtime Schema** | PostgreSQL | Channels, messages tables and publish function |
|
|
48
|
+
| **Permission Model** | Grants + RLS (optional) | Controls subscribe and publish access |
|
|
49
|
+
| **Notification Bridge** | pg_notify | Bridges database to Node.js process |
|
|
50
|
+
| **Realtime Manager** | Node.js | Listens for notifications, dispatches messages |
|
|
51
|
+
| **WebSocket Server** | Socket.IO | Bidirectional client communication |
|
|
52
|
+
| **Webhook Sender** | Axios | HTTP delivery to external endpoints |
|
|
53
|
+
| **SDK** | @insforge/sdk | Client-side subscription and messaging |
|
|
54
|
+
|
|
55
|
+
## Database Schema
|
|
56
|
+
|
|
57
|
+
### Channels Table
|
|
58
|
+
|
|
59
|
+
The `realtime.channels` table defines available channel patterns and their configuration:
|
|
60
|
+
|
|
61
|
+
| Column | Type | Description |
|
|
62
|
+
|--------|------|-------------|
|
|
63
|
+
| `id` | UUID | Primary key |
|
|
64
|
+
| `pattern` | TEXT | Channel name pattern (e.g., `orders`, `order:%`) |
|
|
65
|
+
| `description` | TEXT | Human-readable description |
|
|
66
|
+
| `webhook_urls` | TEXT[] | Array of webhook endpoints |
|
|
67
|
+
| `enabled` | BOOLEAN | Whether the channel is active |
|
|
68
|
+
|
|
69
|
+
<Note>
|
|
70
|
+
Channel patterns use `:` as separator and `%` for wildcards (SQL LIKE pattern). For example, `order:%` matches `order:123`, `order:456`, etc.
|
|
71
|
+
</Note>
|
|
72
|
+
|
|
73
|
+
### Messages Table
|
|
74
|
+
|
|
75
|
+
The `realtime.messages` table stores all published messages for audit purposes:
|
|
76
|
+
|
|
77
|
+
| Column | Type | Description |
|
|
78
|
+
|--------|------|-------------|
|
|
79
|
+
| `id` | UUID | Primary key |
|
|
80
|
+
| `event_name` | TEXT | Event type (e.g., `order_created`) |
|
|
81
|
+
| `channel_id` | UUID | Reference to channels table |
|
|
82
|
+
| `channel_name` | TEXT | Resolved channel name (e.g., `order:123`) |
|
|
83
|
+
| `payload` | JSONB | Event data |
|
|
84
|
+
| `sender_type` | TEXT | `system` (trigger) or `user` (client) |
|
|
85
|
+
| `sender_id` | UUID | User ID for client-initiated messages |
|
|
86
|
+
| `ws_audience_count` | INTEGER | WebSocket subscribers at time of delivery |
|
|
87
|
+
| `wh_audience_count` | INTEGER | Webhook URLs configured |
|
|
88
|
+
| `wh_delivered_count` | INTEGER | Successful webhook deliveries |
|
|
89
|
+
|
|
90
|
+
## Permission Model
|
|
91
|
+
|
|
92
|
+
InsForge Realtime uses PostgreSQL grants and optional Row Level Security (RLS) to control channel access.
|
|
93
|
+
|
|
94
|
+
<Note>
|
|
95
|
+
**RLS is disabled by default** for the best developer experience. Channels and messages are open to all authenticated and anonymous users out of the box. Enable RLS when you need fine-grained access control.
|
|
96
|
+
</Note>
|
|
97
|
+
|
|
98
|
+
### Default Permissions (RLS Disabled)
|
|
99
|
+
|
|
100
|
+
| Permission | Table | Grant | Access |
|
|
101
|
+
|------------|-------|-------|--------|
|
|
102
|
+
| **Subscribe** | `realtime.channels` | SELECT | All authenticated/anon users |
|
|
103
|
+
| **Publish** | `realtime.messages` | INSERT | All authenticated/anon users |
|
|
104
|
+
|
|
105
|
+
### Enabling Access Control
|
|
106
|
+
|
|
107
|
+
To restrict access, enable RLS and add policies:
|
|
108
|
+
|
|
109
|
+
```sql
|
|
110
|
+
-- Step 1: Enable RLS
|
|
111
|
+
ALTER TABLE realtime.channels ENABLE ROW LEVEL SECURITY;
|
|
112
|
+
ALTER TABLE realtime.messages ENABLE ROW LEVEL SECURITY;
|
|
113
|
+
|
|
114
|
+
-- Step 2: Add policies (see examples below)
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
### How RLS Works (When Enabled)
|
|
118
|
+
|
|
119
|
+
| Permission | Table | Policy Type | Description |
|
|
120
|
+
|------------|-------|-------------|-------------|
|
|
121
|
+
| **Subscribe** | `realtime.channels` | SELECT | Who can subscribe to a channel |
|
|
122
|
+
| **Publish** | `realtime.messages` | INSERT | Who can publish to a channel |
|
|
123
|
+
|
|
124
|
+
1. When a client subscribes, the backend executes a SELECT query on `realtime.channels` with the user's role
|
|
125
|
+
2. RLS policies filter the result. If a matching channel is returned, subscription is allowed
|
|
126
|
+
3. When a client publishes, the backend attempts an INSERT into `realtime.messages`
|
|
127
|
+
4. RLS policies evaluate the INSERT. If allowed, the message is stored and broadcast
|
|
128
|
+
|
|
129
|
+
### Helper Function
|
|
130
|
+
|
|
131
|
+
Use `realtime.channel_name()` in your policies to access the channel being requested:
|
|
132
|
+
|
|
133
|
+
```sql
|
|
134
|
+
-- Allow authenticated users to subscribe to their own order channels
|
|
135
|
+
CREATE POLICY "users_can_subscribe_own_orders"
|
|
136
|
+
ON realtime.channels
|
|
137
|
+
FOR SELECT
|
|
138
|
+
TO authenticated
|
|
139
|
+
USING (
|
|
140
|
+
pattern = 'order:%'
|
|
141
|
+
AND EXISTS (
|
|
142
|
+
SELECT 1 FROM orders
|
|
143
|
+
WHERE id = NULLIF(split_part(realtime.channel_name(), ':', 2), '')::uuid
|
|
144
|
+
AND user_id = auth.uid()
|
|
145
|
+
)
|
|
146
|
+
);
|
|
147
|
+
```
|
|
148
|
+
|
|
149
|
+
## Message Flow
|
|
150
|
+
|
|
151
|
+
### System Events (Database Triggers)
|
|
152
|
+
|
|
153
|
+
```mermaid
|
|
154
|
+
sequenceDiagram
|
|
155
|
+
participant App as Application
|
|
156
|
+
participant DB as PostgreSQL
|
|
157
|
+
participant Pub as publish()
|
|
158
|
+
participant Msg as messages table
|
|
159
|
+
participant Manager as Realtime Manager
|
|
160
|
+
participant WS as WebSocket Clients
|
|
161
|
+
participant WH as Webhooks
|
|
162
|
+
|
|
163
|
+
App->>DB: INSERT/UPDATE/DELETE
|
|
164
|
+
DB->>Pub: Trigger fires
|
|
165
|
+
Pub->>Msg: INSERT message
|
|
166
|
+
Msg->>Manager: pg_notify with message_id
|
|
167
|
+
Manager->>Msg: Fetch full message
|
|
168
|
+
Manager->>WS: Broadcast to room
|
|
169
|
+
Manager->>WH: POST to webhook URLs
|
|
170
|
+
Manager->>Msg: Update delivery stats
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
### Client Events (User-Initiated)
|
|
174
|
+
|
|
175
|
+
```mermaid
|
|
176
|
+
sequenceDiagram
|
|
177
|
+
participant Client as SDK Client
|
|
178
|
+
participant Socket as Socket.IO
|
|
179
|
+
participant Msg as messages table
|
|
180
|
+
participant RLS as RLS Policies
|
|
181
|
+
participant Manager as Realtime Manager
|
|
182
|
+
|
|
183
|
+
Client->>Socket: realtime:publish
|
|
184
|
+
Socket->>Msg: insertMessage()
|
|
185
|
+
Msg->>RLS: Evaluate INSERT policy
|
|
186
|
+
Note over Msg: Trigger fires pg_notify
|
|
187
|
+
Manager->>Msg: Fetch message
|
|
188
|
+
Manager->>Socket: Broadcast to room
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
## Publish Function
|
|
192
|
+
|
|
193
|
+
The `realtime.publish()` function is called by your database triggers:
|
|
194
|
+
|
|
195
|
+
```sql
|
|
196
|
+
CREATE OR REPLACE FUNCTION notify_order_changes()
|
|
197
|
+
RETURNS TRIGGER AS $$
|
|
198
|
+
BEGIN
|
|
199
|
+
PERFORM realtime.publish(
|
|
200
|
+
'order:' || NEW.id::text, -- channel name
|
|
201
|
+
TG_OP || '_order', -- event: INSERT_order, UPDATE_order, etc.
|
|
202
|
+
jsonb_build_object(
|
|
203
|
+
'id', NEW.id,
|
|
204
|
+
'status', NEW.status,
|
|
205
|
+
'total', NEW.total
|
|
206
|
+
)
|
|
207
|
+
);
|
|
208
|
+
RETURN NEW;
|
|
209
|
+
END;
|
|
210
|
+
$$ LANGUAGE plpgsql SECURITY DEFINER;
|
|
211
|
+
|
|
212
|
+
CREATE TRIGGER order_changes_trigger
|
|
213
|
+
AFTER INSERT OR UPDATE ON orders
|
|
214
|
+
FOR EACH ROW
|
|
215
|
+
EXECUTE FUNCTION notify_order_changes();
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
<Warning>
|
|
219
|
+
The `realtime.publish()` function can only be called by database triggers (SECURITY DEFINER). It bypasses RLS to insert system messages.
|
|
220
|
+
</Warning>
|
|
221
|
+
|
|
222
|
+
## WebSocket Events
|
|
223
|
+
|
|
224
|
+
### Client-to-Server Events
|
|
225
|
+
|
|
226
|
+
| Event | Payload | Description |
|
|
227
|
+
|-------|---------|-------------|
|
|
228
|
+
| `realtime:subscribe` | `{ channel: string }` | Subscribe to a channel |
|
|
229
|
+
| `realtime:unsubscribe` | `{ channel: string }` | Unsubscribe from a channel |
|
|
230
|
+
| `realtime:publish` | `{ channel, event, payload }` | Publish a message |
|
|
231
|
+
|
|
232
|
+
### Server-to-Client Events
|
|
233
|
+
|
|
234
|
+
| Event | Payload | Description |
|
|
235
|
+
|-------|---------|-------------|
|
|
236
|
+
| `{eventName}` | Message payload + meta | Custom event from channel |
|
|
237
|
+
| `realtime:error` | `{ code, message }` | Error notification |
|
|
238
|
+
|
|
239
|
+
### Socket Message Structure
|
|
240
|
+
|
|
241
|
+
All WebSocket messages include a `meta` object with server-enforced fields alongside the event payload:
|
|
242
|
+
|
|
243
|
+
```typescript
|
|
244
|
+
interface SocketMessage {
|
|
245
|
+
meta: {
|
|
246
|
+
channel?: string // Channel the message was sent to
|
|
247
|
+
messageId: string // Unique message ID (UUID)
|
|
248
|
+
senderType: 'system' | 'user'
|
|
249
|
+
senderId?: string // User ID for client messages
|
|
250
|
+
timestamp: Date // Server timestamp
|
|
251
|
+
}
|
|
252
|
+
// ...event payload fields
|
|
253
|
+
}
|
|
254
|
+
```
|
|
255
|
+
|
|
256
|
+
## Webhook Delivery
|
|
257
|
+
|
|
258
|
+
When channels have `webhook_urls` configured, messages are delivered via HTTP POST:
|
|
259
|
+
|
|
260
|
+
### Request Format
|
|
261
|
+
|
|
262
|
+
```http
|
|
263
|
+
POST /your-webhook-endpoint HTTP/1.1
|
|
264
|
+
Content-Type: application/json
|
|
265
|
+
X-InsForge-Event: order_created
|
|
266
|
+
X-InsForge-Channel: order:123
|
|
267
|
+
X-InsForge-Message-Id: a1b2c3d4-e5f6-...
|
|
268
|
+
|
|
269
|
+
{
|
|
270
|
+
"id": "123",
|
|
271
|
+
"status": "confirmed",
|
|
272
|
+
"total": 99.99
|
|
273
|
+
}
|
|
274
|
+
```
|
|
275
|
+
|
|
276
|
+
### Delivery Guarantees
|
|
277
|
+
|
|
278
|
+
| Feature | Behavior |
|
|
279
|
+
|---------|----------|
|
|
280
|
+
| **Retries** | 2 retries with 1s, 2s backoff |
|
|
281
|
+
| **Timeout** | 10 seconds per request |
|
|
282
|
+
| **Parallel** | All webhook URLs called concurrently |
|
|
283
|
+
| **Tracking** | Success/failure counts stored per message |
|
|
284
|
+
|
|
285
|
+
## Sender Types
|
|
286
|
+
|
|
287
|
+
| Type | Source | Description |
|
|
288
|
+
|------|--------|-------------|
|
|
289
|
+
| **system** | Database triggers | Events from `realtime.publish()` function |
|
|
290
|
+
| **user** | Client SDK | Events from `insforge.realtime.publish()` |
|
|
291
|
+
|
|
292
|
+
<Tip>
|
|
293
|
+
System events are trusted and bypass publish RLS checks. User events must pass INSERT policy on `realtime.messages`.
|
|
294
|
+
</Tip>
|
|
295
|
+
|
|
296
|
+
## Developer Workflow
|
|
297
|
+
|
|
298
|
+
<Steps>
|
|
299
|
+
<Step title="Define Channels">
|
|
300
|
+
Create channel patterns in `realtime.channels`:
|
|
301
|
+
```sql
|
|
302
|
+
INSERT INTO realtime.channels (pattern, description)
|
|
303
|
+
VALUES ('order:%', 'Order-specific events');
|
|
304
|
+
```
|
|
305
|
+
</Step>
|
|
306
|
+
|
|
307
|
+
<Step title="Configure Permissions (Optional)">
|
|
308
|
+
RLS is disabled by default, so all users can subscribe and publish. To restrict access, enable RLS and add policies:
|
|
309
|
+
```sql
|
|
310
|
+
-- Step 1: Enable RLS
|
|
311
|
+
ALTER TABLE realtime.channels ENABLE ROW LEVEL SECURITY;
|
|
312
|
+
ALTER TABLE realtime.messages ENABLE ROW LEVEL SECURITY;
|
|
313
|
+
|
|
314
|
+
-- Step 2: Add policies
|
|
315
|
+
-- Subscribe: users can only subscribe to their own order channels
|
|
316
|
+
CREATE POLICY "users_subscribe_own_orders"
|
|
317
|
+
ON realtime.channels FOR SELECT
|
|
318
|
+
TO authenticated
|
|
319
|
+
USING (
|
|
320
|
+
pattern = 'order:%'
|
|
321
|
+
AND EXISTS (
|
|
322
|
+
SELECT 1 FROM orders
|
|
323
|
+
WHERE id = NULLIF(split_part(realtime.channel_name(), ':', 2), '')::uuid
|
|
324
|
+
AND user_id = auth.uid()
|
|
325
|
+
)
|
|
326
|
+
);
|
|
327
|
+
|
|
328
|
+
-- Publish: only admins can publish to order channels
|
|
329
|
+
CREATE POLICY "admins_publish_orders"
|
|
330
|
+
ON realtime.messages FOR INSERT
|
|
331
|
+
TO authenticated
|
|
332
|
+
WITH CHECK (
|
|
333
|
+
channel_name LIKE 'order:%'
|
|
334
|
+
AND EXISTS (
|
|
335
|
+
SELECT 1 FROM admins
|
|
336
|
+
WHERE user_id = auth.uid()
|
|
337
|
+
)
|
|
338
|
+
);
|
|
339
|
+
```
|
|
340
|
+
</Step>
|
|
341
|
+
|
|
342
|
+
<Step title="Create Triggers">
|
|
343
|
+
Add trigger function and trigger to emit events on database changes:
|
|
344
|
+
```sql
|
|
345
|
+
CREATE OR REPLACE FUNCTION notify_order_changes()
|
|
346
|
+
RETURNS TRIGGER AS $$
|
|
347
|
+
BEGIN
|
|
348
|
+
PERFORM realtime.publish(
|
|
349
|
+
'order:' || NEW.id::text,
|
|
350
|
+
TG_OP || '_order',
|
|
351
|
+
jsonb_build_object('id', NEW.id, 'status', NEW.status)
|
|
352
|
+
);
|
|
353
|
+
RETURN NEW;
|
|
354
|
+
END;
|
|
355
|
+
$$ LANGUAGE plpgsql SECURITY DEFINER;
|
|
356
|
+
|
|
357
|
+
CREATE TRIGGER order_realtime
|
|
358
|
+
AFTER INSERT OR UPDATE ON orders
|
|
359
|
+
FOR EACH ROW EXECUTE FUNCTION notify_order_changes();
|
|
360
|
+
```
|
|
361
|
+
</Step>
|
|
362
|
+
|
|
363
|
+
<Step title="Subscribe in Client">
|
|
364
|
+
Use the SDK to subscribe and listen:
|
|
365
|
+
```javascript
|
|
366
|
+
await insforge.realtime.connect()
|
|
367
|
+
await insforge.realtime.subscribe('order:123')
|
|
368
|
+
insforge.realtime.on('UPDATE_order', (data) => {
|
|
369
|
+
console.log('Order updated:', data)
|
|
370
|
+
})
|
|
371
|
+
```
|
|
372
|
+
</Step>
|
|
373
|
+
</Steps>
|
|
374
|
+
|
|
375
|
+
## Architecture Features
|
|
376
|
+
|
|
377
|
+
<CardGroup cols={2}>
|
|
378
|
+
<Card title="Database-Driven" icon="database">
|
|
379
|
+
Events originate from PostgreSQL triggers, ensuring consistency with your data
|
|
380
|
+
</Card>
|
|
381
|
+
|
|
382
|
+
<Card title="Optional RLS Security" icon="shield">
|
|
383
|
+
Works out of the box, with optional RLS for fine-grained access control
|
|
384
|
+
</Card>
|
|
385
|
+
|
|
386
|
+
<Card title="Dual Delivery" icon="arrows-split-up-and-left">
|
|
387
|
+
Messages delivered to both WebSocket clients and webhook endpoints simultaneously
|
|
388
|
+
</Card>
|
|
389
|
+
|
|
390
|
+
<Card title="Audit Trail" icon="clipboard-list">
|
|
391
|
+
All messages stored in database with delivery statistics for debugging and replay
|
|
392
|
+
</Card>
|
|
393
|
+
|
|
394
|
+
<Card title="Pattern Matching" icon="asterisk">
|
|
395
|
+
Wildcard channel patterns let you define permissions for dynamic channels
|
|
396
|
+
</Card>
|
|
397
|
+
|
|
398
|
+
<Card title="Bidirectional" icon="arrows-left-right">
|
|
399
|
+
Clients can both receive events and publish their own messages (subject to RLS)
|
|
400
|
+
</Card>
|
|
401
|
+
</CardGroup>
|
|
402
|
+
|
|
403
|
+
## Performance Characteristics
|
|
404
|
+
|
|
405
|
+
| Metric | Value | Notes |
|
|
406
|
+
|--------|-------|-------|
|
|
407
|
+
| **Latency** | ~10-50ms | Database to client, depends on network |
|
|
408
|
+
| **Throughput** | High | Limited by PostgreSQL NOTIFY and Socket.IO |
|
|
409
|
+
| **Persistence** | Full | All messages stored in database |
|
|
410
|
+
| **Reconnection** | Automatic | Socket.IO handles reconnection |
|
|
411
|
+
| **Webhook Timeout** | 10s | Per webhook request |
|
|
412
|
+
|
|
413
|
+
## Best Practices
|
|
414
|
+
|
|
415
|
+
<CardGroup cols={2}>
|
|
416
|
+
<Card title="Keep Payloads Small" icon="compress">
|
|
417
|
+
Only include necessary data in payloads
|
|
418
|
+
</Card>
|
|
419
|
+
|
|
420
|
+
<Card title="Use Specific Channels" icon="bullseye">
|
|
421
|
+
Prefer `order:123` over broadcasting to `orders` for reducing the traffic
|
|
422
|
+
</Card>
|
|
423
|
+
|
|
424
|
+
<Card title="Add RLS When Needed" icon="gavel">
|
|
425
|
+
Enable RLS and add policies when you need to restrict channel access
|
|
426
|
+
</Card>
|
|
427
|
+
|
|
428
|
+
<Card title="Monitor Delivery" icon="chart-bar">
|
|
429
|
+
Check `ws_audience_count` and `wh_delivered_count` to debug delivery issues
|
|
430
|
+
</Card>
|
|
431
|
+
|
|
432
|
+
<Card title="Handle Reconnection" icon="rotate">
|
|
433
|
+
Design clients to refetch state on reconnect since missed messages are not replayed
|
|
434
|
+
</Card>
|
|
435
|
+
|
|
436
|
+
<Card title="Use Webhooks for Reliability" icon="webhook">
|
|
437
|
+
For critical notifications, configure webhook URLs as backup delivery method
|
|
438
|
+
</Card>
|
|
439
|
+
</CardGroup>
|
|
440
|
+
|
|
441
|
+
## Limitations
|
|
442
|
+
|
|
443
|
+
- **No Message Replay**: Clients don't receive messages missed during disconnection
|
|
444
|
+
- **No Presence**: No built-in tracking of who's online in a channel
|
|
445
|
+
- **Single Region**: Messages delivered from single backend instance
|
|
446
|
+
- **Webhook Retries**: Limited to 2 retries with short timeout
|