From 3096d3e8f70a0080aca83a88a253ae6866ed8301 Mon Sep 17 00:00:00 2001 From: Waleed Latif Date: Sat, 1 Aug 2026 10:25:07 -0700 Subject: [PATCH 1/2] refactor(dev): remove the minimal-registry escape hatch MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `dev:minimal` existed because the tool registry was 71-82% of every workspace route's module graph and aliasing it away was the only way to make dev bearable. The metadata work removed that reason, so the hatch now buys almost nothing: before this stack 31.7s -> 20.0s cold (-37%) after this stack 22.9s -> 20.7s cold (-10%) A 10% cold-compile win, on the run that happens once — restarts are ~4.2s either way — is not worth what it costs. `tools/registry.minimal.ts` and `blocks/registry-maps.minimal.ts` are 283 lines of hand-curated duplicates of the real registries that **nothing keeps in sync** (no lint, no CI check, no test); they are correct today only because someone remembered. And the mode is actively misleading: it silently drops ~250 services and ~280 blocks, so anything reproduced under it may not reproduce for real. Removes both files, the `SIM_DEV_MINIMAL_REGISTRY` branch from `next.config.ts` (including the whole `webpack()` hook, which existed only for this), and the `dev:minimal` / `dev:full:minimal-registry` scripts. Verified after removal: `tsc` clean, boundary + metadata + skills + monorepo gates pass, and `next dev` starts and serves the canvas at 22.6s cold / HTTP 200. --- apps/sim/blocks/registry-maps.minimal.ts | 93 ----------- apps/sim/next.config.ts | 42 ----- apps/sim/package.json | 1 - apps/sim/tools/registry.minimal.ts | 190 ----------------------- package.json | 1 - 5 files changed, 327 deletions(-) delete mode 100644 apps/sim/blocks/registry-maps.minimal.ts delete mode 100644 apps/sim/tools/registry.minimal.ts diff --git a/apps/sim/blocks/registry-maps.minimal.ts b/apps/sim/blocks/registry-maps.minimal.ts deleted file mode 100644 index 39ab88a9ed1..00000000000 --- a/apps/sim/blocks/registry-maps.minimal.ts +++ /dev/null @@ -1,93 +0,0 @@ -import { A2ABlock } from '@/blocks/blocks/a2a' -import { AgentBlock } from '@/blocks/blocks/agent' -import { ApiBlock } from '@/blocks/blocks/api' -import { ConditionBlock } from '@/blocks/blocks/condition' -import { CredentialBlock } from '@/blocks/blocks/credential' -import { DeploymentsBlock } from '@/blocks/blocks/deployments' -import { EnrichmentBlock } from '@/blocks/blocks/enrichment' -import { EvaluatorBlock } from '@/blocks/blocks/evaluator' -import { FileV5Block } from '@/blocks/blocks/file' -import { FunctionBlock } from '@/blocks/blocks/function' -import { GenericWebhookBlock } from '@/blocks/blocks/generic_webhook' -import { GmailV2Block } from '@/blocks/blocks/gmail' -import { GuardrailsBlock } from '@/blocks/blocks/guardrails' -import { HumanInTheLoopBlock } from '@/blocks/blocks/human_in_the_loop' -import { ImapBlock } from '@/blocks/blocks/imap' -import { KnowledgeBlock } from '@/blocks/blocks/knowledge' -import { LogsV2Block } from '@/blocks/blocks/logs' -import { McpBlock } from '@/blocks/blocks/mcp' -import { MemoryBlock } from '@/blocks/blocks/memory' -import { NoteBlock } from '@/blocks/blocks/note' -import { ResponseBlock } from '@/blocks/blocks/response' -import { RouterV2Block } from '@/blocks/blocks/router' -import { RssBlock } from '@/blocks/blocks/rss' -import { ScheduleBlock } from '@/blocks/blocks/schedule' -import { SearchBlock } from '@/blocks/blocks/search' -import { SimWorkspaceEventBlock } from '@/blocks/blocks/sim_workspace_event' -import { SlackBlock, SlackV2Block } from '@/blocks/blocks/slack' -import { StartTriggerBlock } from '@/blocks/blocks/start_trigger' -import { TableBlock } from '@/blocks/blocks/table' -import { TableV2Block } from '@/blocks/blocks/table_v2' -import { TranslateBlock } from '@/blocks/blocks/translate' -import { VariablesBlock } from '@/blocks/blocks/variables' -import { WaitBlock } from '@/blocks/blocks/wait' -import { WebhookRequestBlock } from '@/blocks/blocks/webhook_request' -import { WorkflowInputBlock } from '@/blocks/blocks/workflow_input' -import type { BlockConfig, BlockMeta } from '@/blocks/types' - -/** - * Dev-only minimal block maps. Swapped in for `@/blocks/registry-maps` via a - * resolve-alias when `SIM_DEV_MINIMAL_REGISTRY=1` (see next.config.ts) so the - * dev server only compiles a curated core set of block configs instead of all - * ~268. The set is drawn from the canonical, toolbar-visible blocks - * (`category: 'blocks'` / `'triggers'`, not `hideFromToolbar`, always the latest - * version — never a superseded one). The ~247 `category: 'tools'` integrations - * are excluded (that is the heavy graph minimal mode exists to skip) — except - * `slack`/`slack_v2` and `gmail_v2`, kept as the everyday integrations (their - * tools are likewise included in `tools/registry.minimal.ts`) — and so are - * a few heavy or rarely-core-dev blocks pruned by hand: `mothership` and `pi` - * (chunkiest configs), the media blocks `tts` / `stt_v2` / `image_generator_v2` - * / `video_generator_v3`, and the `circleback` meeting-notetaker integration - * trigger. Only these blocks resolve in the editor/executor in minimal mode; - * unset the flag for the full set. NEVER aliased in production. - */ -export const BLOCK_REGISTRY: Record = { - a2a: A2ABlock, - agent: AgentBlock, - api: ApiBlock, - condition: ConditionBlock, - credential: CredentialBlock, - deployments: DeploymentsBlock, - enrichment: EnrichmentBlock, - evaluator: EvaluatorBlock, - file_v5: FileV5Block, - function: FunctionBlock, - gmail_v2: GmailV2Block, - generic_webhook: GenericWebhookBlock, - guardrails: GuardrailsBlock, - human_in_the_loop: HumanInTheLoopBlock, - imap: ImapBlock, - knowledge: KnowledgeBlock, - logs_v2: LogsV2Block, - mcp: McpBlock, - memory: MemoryBlock, - note: NoteBlock, - response: ResponseBlock, - router_v2: RouterV2Block, - rss: RssBlock, - schedule: ScheduleBlock, - search: SearchBlock, - sim_workspace_event: SimWorkspaceEventBlock, - slack: SlackBlock, - slack_v2: SlackV2Block, - start_trigger: StartTriggerBlock, - table: TableBlock, - table_v2: TableV2Block, - translate: TranslateBlock, - variables: VariablesBlock, - wait: WaitBlock, - webhook_request: WebhookRequestBlock, - workflow_input: WorkflowInputBlock, -} - -export const BLOCK_META_REGISTRY: Record = {} diff --git a/apps/sim/next.config.ts b/apps/sim/next.config.ts index 356e564ae9a..735ea2aff5f 100644 --- a/apps/sim/next.config.ts +++ b/apps/sim/next.config.ts @@ -8,34 +8,6 @@ import { getWorkflowExecutionCSPPolicy, } from './lib/core/security/csp' -/** - * Dev-only escape hatch: when `SIM_DEV_MINIMAL_REGISTRY=1` (`bun run dev:minimal`), - * swap the heavy block and tool registries for tiny curated variants via a - * Turbopack/webpack resolve alias. - * - * The tool registry (4,351 entries across 261 service dirs) pulls ~5,907 modules - * and is 68-78% of every workspace route's module graph; aliasing it away takes - * `app/workspace/layout.tsx` from 5,916 modules to 1,255. Blocks are NOT a - * co-equal cost - `blocks/registry-maps` alone accounts for ~349 modules and - * mostly rides in behind the tool registry. - * - * It is reached through ONE choke point (`tools/utils.ts` → `@/tools/registry`) - * fed by four redundant client-reachable edges: providers/utils → tools/params, - * lib/workflows/blocks/block-outputs, lib/workflows/sanitization/validation, and - * serializer/index. All four must be severed for any of them to matter, which is - * why cutting only the providers/utils edge buys a single module. - * - * Only the curated core blocks/tools work in this mode. Never enabled in - * production - the minimal variants genuinely drop ~250 services and ~280 blocks. - */ -const useMinimalRegistry = isDev && process.env.SIM_DEV_MINIMAL_REGISTRY === '1' -const minimalRegistryAlias: Record = useMinimalRegistry - ? { - '@/tools/registry': './tools/registry.minimal.ts', - '@/blocks/registry-maps': './blocks/registry-maps.minimal.ts', - } - : {} - /** * Marketing routes (`app/(landing)/**`, plus the root) exempted from COEP. * @@ -77,20 +49,6 @@ const nextConfig: NextConfig = { productionBrowserSourceMaps: true, turbopack: { root: path.join(import.meta.dirname, '../..'), - resolveAlias: minimalRegistryAlias, - }, - webpack: (config) => { - if (useMinimalRegistry) { - config.resolve.alias = { - ...config.resolve.alias, - '@/tools/registry$': path.resolve(import.meta.dirname, 'tools/registry.minimal.ts'), - '@/blocks/registry-maps$': path.resolve( - import.meta.dirname, - 'blocks/registry-maps.minimal.ts' - ), - } - } - return config }, images: { formats: ['image/avif', 'image/webp'], diff --git a/apps/sim/package.json b/apps/sim/package.json index 9ceebd08d2f..8c80ad3436b 100644 --- a/apps/sim/package.json +++ b/apps/sim/package.json @@ -9,7 +9,6 @@ }, "scripts": { "dev": "bun run dev:cache:cap && next dev --port 3000", - "dev:minimal": "bun run dev:cache:cap && SIM_DEV_MINIMAL_REGISTRY=1 next dev --port 3000", "dev:capped": "bun run dev:cache:cap && NODE_OPTIONS='--max-old-space-size=4096' next dev --port 3000", "dev:cache:cap": "bun run ../../scripts/prune-turbopack-cache.ts", "dev:clean": "rm -rf .next/dev/cache", diff --git a/apps/sim/tools/registry.minimal.ts b/apps/sim/tools/registry.minimal.ts deleted file mode 100644 index 899124191ce..00000000000 --- a/apps/sim/tools/registry.minimal.ts +++ /dev/null @@ -1,190 +0,0 @@ -import { functionExecuteTool } from '@/tools/function' -import { - gmailAddLabelV2Tool, - gmailArchiveV2Tool, - gmailCreateLabelV2Tool, - gmailDeleteDraftV2Tool, - gmailDeleteLabelV2Tool, - gmailDeleteV2Tool, - gmailDraftV2Tool, - gmailEditDraftV2Tool, - gmailGetDraftV2Tool, - gmailGetThreadV2Tool, - gmailListDraftsV2Tool, - gmailListLabelsV2Tool, - gmailListThreadsV2Tool, - gmailMarkReadV2Tool, - gmailMarkUnreadV2Tool, - gmailMoveV2Tool, - gmailReadV2Tool, - gmailRemoveLabelV2Tool, - gmailSearchV2Tool, - gmailSendV2Tool, - gmailTrashThreadV2Tool, - gmailUnarchiveV2Tool, - gmailUntrashThreadV2Tool, - gmailUpdateLabelV2Tool, -} from '@/tools/gmail' -import { guardrailsValidateTool } from '@/tools/guardrails' -import { httpRequestTool } from '@/tools/http' -import { - slackAddReactionTool, - slackArchiveConversationTool, - slackCanvasTool, - slackCreateChannelCanvasTool, - slackCreateConversationTool, - slackDeleteCanvasTool, - slackDeleteMessageTool, - slackDeleteScheduledMessageTool, - slackDownloadTool, - slackEditCanvasTool, - slackEphemeralMessageTool, - slackGetCanvasTool, - slackGetChannelHistoryTool, - slackGetChannelInfoTool, - slackGetMessageTool, - slackGetPermalinkTool, - slackGetThreadRepliesTool, - slackGetThreadTool, - slackGetUserPresenceTool, - slackGetUserTool, - slackInviteToConversationTool, - slackListCanvasesTool, - slackListChannelsTool, - slackListMembersTool, - slackListScheduledMessagesTool, - slackListUsersTool, - slackLookupCanvasSectionsTool, - slackMessageReaderTool, - slackMessageTool, - slackOpenViewTool, - slackPublishViewTool, - slackPushViewTool, - slackRemoveReactionTool, - slackRenameConversationTool, - slackScheduleMessageTool, - slackSetConversationPurposeTool, - slackSetConversationTopicTool, - slackSetStatusTool, - slackSetSuggestedPromptsTool, - slackSetTitleTool, - slackUpdateMessageTool, - slackUpdateViewTool, -} from '@/tools/slack' -import { - tableBatchInsertRowsTool, - tableCreateTool, - tableDeleteRowsByFilterTool, - tableDeleteRowTool, - tableGetRowTool, - tableGetSchemaTool, - tableInsertRowTool, - tableListTool, - tableQueryRowsTool, - tableQueryRowsV2Tool, - tableUpdateRowsByFilterTool, - tableUpdateRowTool, - tableUpsertRowTool, -} from '@/tools/table' -import type { ToolConfig } from '@/tools/types' -import { customBlockExecutorTool, workflowExecutorTool } from '@/tools/workflow' - -/** - * Dev-only minimal tool registry. Swapped in for `@/tools/registry` via a - * Turbopack/webpack resolve-alias when `SIM_DEV_MINIMAL_REGISTRY=1` (see - * next.config.ts) so the local dev server never compiles the full ~247-tool - * graph (~2,074 modules) that the shared workspace layout otherwise drags into - * every route. Only these tools execute in minimal mode; unset the flag for the - * full set. The slack and gmail v2 sets back the `slack`/`slack_v2` and - * `gmail_v2` blocks kept in `blocks/registry-maps.minimal.ts`. NEVER aliased in - * production. - */ -export const tools: Record = { - http_request: httpRequestTool, - function_execute: functionExecuteTool, - // Table block operations (v1 + v2 Table blocks are both runnable in minimal mode). - table_query_rows: tableQueryRowsTool, - table_insert_row: tableInsertRowTool, - table_batch_insert_rows: tableBatchInsertRowsTool, - table_upsert_row: tableUpsertRowTool, - table_update_row: tableUpdateRowTool, - table_update_rows_by_filter: tableUpdateRowsByFilterTool, - table_delete_row: tableDeleteRowTool, - table_delete_rows_by_filter: tableDeleteRowsByFilterTool, - table_query_rows_v2: tableQueryRowsV2Tool, - table_get_row: tableGetRowTool, - table_get_schema: tableGetSchemaTool, - table_create: tableCreateTool, - table_list: tableListTool, - guardrails_validate: guardrailsValidateTool, - // Needed so workflow-as-tool and custom (deploy-as-block) tools resolve their - // config in minimal-registry dev mode (both route through `workflow_executor`). - workflow_executor: workflowExecutorTool, - deployed_block_executor: customBlockExecutorTool, - gmail_send_v2: gmailSendV2Tool, - gmail_read_v2: gmailReadV2Tool, - gmail_search_v2: gmailSearchV2Tool, - gmail_draft_v2: gmailDraftV2Tool, - gmail_move_v2: gmailMoveV2Tool, - gmail_mark_read_v2: gmailMarkReadV2Tool, - gmail_mark_unread_v2: gmailMarkUnreadV2Tool, - gmail_archive_v2: gmailArchiveV2Tool, - gmail_unarchive_v2: gmailUnarchiveV2Tool, - gmail_delete_v2: gmailDeleteV2Tool, - gmail_add_label_v2: gmailAddLabelV2Tool, - gmail_remove_label_v2: gmailRemoveLabelV2Tool, - gmail_create_label_v2: gmailCreateLabelV2Tool, - gmail_delete_draft_v2: gmailDeleteDraftV2Tool, - gmail_delete_label_v2: gmailDeleteLabelV2Tool, - gmail_edit_draft_v2: gmailEditDraftV2Tool, - gmail_get_draft_v2: gmailGetDraftV2Tool, - gmail_get_thread_v2: gmailGetThreadV2Tool, - gmail_list_drafts_v2: gmailListDraftsV2Tool, - gmail_list_labels_v2: gmailListLabelsV2Tool, - gmail_list_threads_v2: gmailListThreadsV2Tool, - gmail_trash_thread_v2: gmailTrashThreadV2Tool, - gmail_untrash_thread_v2: gmailUntrashThreadV2Tool, - gmail_update_label_v2: gmailUpdateLabelV2Tool, - slack_add_reaction: slackAddReactionTool, - slack_archive_conversation: slackArchiveConversationTool, - slack_canvas: slackCanvasTool, - slack_create_channel_canvas: slackCreateChannelCanvasTool, - slack_create_conversation: slackCreateConversationTool, - slack_delete_canvas: slackDeleteCanvasTool, - slack_delete_message: slackDeleteMessageTool, - slack_delete_scheduled_message: slackDeleteScheduledMessageTool, - slack_download: slackDownloadTool, - slack_edit_canvas: slackEditCanvasTool, - slack_ephemeral_message: slackEphemeralMessageTool, - slack_get_canvas: slackGetCanvasTool, - slack_get_channel_history: slackGetChannelHistoryTool, - slack_get_channel_info: slackGetChannelInfoTool, - slack_get_message: slackGetMessageTool, - slack_get_permalink: slackGetPermalinkTool, - slack_get_thread_replies: slackGetThreadRepliesTool, - slack_get_thread: slackGetThreadTool, - slack_get_user_presence: slackGetUserPresenceTool, - slack_get_user: slackGetUserTool, - slack_invite_to_conversation: slackInviteToConversationTool, - slack_list_canvases: slackListCanvasesTool, - slack_list_channels: slackListChannelsTool, - slack_list_members: slackListMembersTool, - slack_list_scheduled_messages: slackListScheduledMessagesTool, - slack_list_users: slackListUsersTool, - slack_lookup_canvas_sections: slackLookupCanvasSectionsTool, - slack_message_reader: slackMessageReaderTool, - slack_message: slackMessageTool, - slack_open_view: slackOpenViewTool, - slack_publish_view: slackPublishViewTool, - slack_push_view: slackPushViewTool, - slack_remove_reaction: slackRemoveReactionTool, - slack_rename_conversation: slackRenameConversationTool, - slack_schedule_message: slackScheduleMessageTool, - slack_set_conversation_purpose: slackSetConversationPurposeTool, - slack_set_conversation_topic: slackSetConversationTopicTool, - slack_set_status: slackSetStatusTool, - slack_set_suggested_prompts: slackSetSuggestedPromptsTool, - slack_set_title: slackSetTitleTool, - slack_update_message: slackUpdateMessageTool, - slack_update_view: slackUpdateViewTool, -} diff --git a/package.json b/package.json index 2ffb8b66c42..3cd37c1d35e 100644 --- a/package.json +++ b/package.json @@ -16,7 +16,6 @@ "dev": "turbo run dev", "dev:sockets": "cd apps/realtime && bun run dev", "dev:full": "bunx concurrently -n \"App,Realtime\" -c \"cyan,magenta\" \"cd apps/sim && bun run dev\" \"cd apps/realtime && bun run dev\"", - "dev:full:minimal-registry": "bunx concurrently -n \"App,Realtime\" -c \"cyan,magenta\" \"cd apps/sim && bun run dev:minimal\" \"cd apps/realtime && bun run dev\"", "dev:full:capped": "bunx concurrently -n \"App,Realtime\" -c \"cyan,magenta\" \"cd apps/sim && bun run dev:capped\" \"cd apps/realtime && bun run dev\"", "test": "turbo run test", "format": "turbo run format", From c9649743d4c78ac9f1b198822865eaab8c0e1bfe Mon Sep 17 00:00:00 2001 From: Waleed Latif Date: Sat, 1 Aug 2026 11:17:05 -0700 Subject: [PATCH 2/2] fix(setup): stop the wizard offering the removed minimal-registry mode MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The setup wizard prompted for a dev server on machines under 16GB and **defaulted** to `dev:full:minimal-registry` — a script this stack deletes. Anyone running `bun run setup` on a low-RAM machine would have accepted the default and hit "Script not found", which is exactly the contributor the mode existed to help. Repointed at `dev:full:capped`, which still exists and caps Node at 4GB without dropping ~250 integrations — a strictly better answer to the same question. The hints were also stale: they warned the full registry "can use 4-5GB+ on its own", which was true when a dev server sat at 11.5GB. It now sits at ~4GB, so they say that instead. Missed by an earlier sweep because the pattern searched for `dev:minimal` and `registry.minimal`, and this string is `dev:full:minimal-registry` — the two halves reversed. Re-swept across every file type for all spellings: zero references remain. Also audited every script value the wizard can return, so the class of bug is checked, not just this instance. --- scripts/setup/modes/dev.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/scripts/setup/modes/dev.ts b/scripts/setup/modes/dev.ts index 5364c165891..4a5d817f1c9 100644 --- a/scripts/setup/modes/dev.ts +++ b/scripts/setup/modes/dev.ts @@ -163,17 +163,17 @@ export async function runDevMode( message: `Low RAM detected (${detection.specs.hostMemGb}GB) — which dev server?`, options: [ { - value: 'dev:full:minimal-registry', - label: 'Minimal block registry (recommended)', - hint: 'much lower memory — loads fewer integration blocks in dev', + value: 'dev:full:capped', + label: 'Capped heap (recommended)', + hint: 'caps Node at 4GB — every integration still available', }, { value: 'dev:full', - label: 'Full registry', - hint: 'every block available — can use 4-5GB+ on its own', + label: 'Uncapped', + hint: 'lets the dev server take what it needs (~4GB typical)', }, ], - initialValue: 'dev:full:minimal-registry', + initialValue: 'dev:full:capped', }) } return {