Skip to content

Commit 75ce888

Browse files
improvement(execution): trigger manual execution using mock payloads (#1863)
* fix(err-message): manual run message * make external triggers start workflow manually too * improvement(execution): trigger manual execution using mock payloads * remove redundant code and update generate mock value func * cleanup code, add to docs * fix multi trigger injection * address greptile comments
1 parent 142d3aa commit 75ce888

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

62 files changed

+458
-3513
lines changed

apps/docs/content/docs/en/triggers/index.mdx

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,3 +39,15 @@ Use the Start block for everything originating from the editor, deploy-to-API, o
3939

4040
> Deployments power every trigger. Update the workflow, redeploy, and all trigger entry points pick up the new snapshot. Learn more in [Execution → Deployment Snapshots](/execution).
4141
42+
## Manual Execution Priority
43+
44+
When you click **Run** in the editor, Sim automatically selects which trigger to execute based on the following priority order:
45+
46+
1. **Start Block** (highest priority)
47+
2. **Schedule Triggers**
48+
3. **External Triggers** (webhooks, integrations like Slack, Gmail, Airtable, etc.)
49+
50+
If your workflow has multiple triggers, the highest priority trigger will be executed. For example, if you have both a Start block and a Webhook trigger, clicking Run will execute the Start block.
51+
52+
**External triggers with mock payloads**: When external triggers (webhooks and integrations) are executed manually, Sim automatically generates mock payloads based on the trigger's expected data structure. This ensures downstream blocks can resolve variables correctly during testing.
53+

apps/sim/app/api/workflows/[id]/execute/route.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ const ExecuteWorkflowSchema = z.object({
2929
stream: z.boolean().optional(),
3030
useDraftState: z.boolean().optional(),
3131
input: z.any().optional(),
32+
startBlockId: z.string().optional(),
3233
})
3334

3435
export const runtime = 'nodejs'

apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel-new/components/editor/components/sub-block/components/webhook/components/providers/gmail.tsx

Lines changed: 0 additions & 84 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,11 @@
11
import { useEffect, useState } from 'react'
22
import { Info } from 'lucide-react'
33
import { Tooltip } from '@/components/emcn'
4-
import { GmailIcon } from '@/components/icons'
54
import {
65
Badge,
76
Button,
87
Checkbox,
98
Label,
10-
Notice,
119
Select,
1210
SelectContent,
1311
SelectItem,
@@ -16,7 +14,6 @@ import {
1614
Skeleton,
1715
} from '@/components/ui'
1816
import { createLogger } from '@/lib/logs/console/logger'
19-
import { JSONView } from '@/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/console/components'
2017
import { ConfigSection } from '@/app/workspace/[workspaceId]/w/[workflowId]/components/panel-new/components/editor/components/sub-block/components/webhook/components'
2118

2219
const logger = createLogger('GmailConfig')
@@ -56,76 +53,6 @@ const formatLabelName = (label: GmailLabel): string => {
5653
return formattedName
5754
}
5855

59-
const getExampleEmailEvent = (includeRawEmail: boolean) => {
60-
const baseExample = {
61-
email: {
62-
id: '18e0ffabd5b5a0f4',
63-
threadId: '18e0ffabd5b5a0f4',
64-
subject: 'Monthly Report - April 2025',
65-
66-
67-
68-
date: '2025-05-10T10:15:23.000Z',
69-
bodyText:
70-
'Hello,\n\nPlease find attached the monthly report for April 2025.\n\nBest regards,\nSender',
71-
bodyHtml:
72-
'<div><p>Hello,</p><p>Please find attached the monthly report for April 2025.</p><p>Best regards,<br>Sender</p></div>',
73-
labels: ['INBOX', 'IMPORTANT'],
74-
hasAttachments: true,
75-
attachments: [
76-
{
77-
filename: 'report-april-2025.pdf',
78-
mimeType: 'application/pdf',
79-
size: 2048576,
80-
},
81-
],
82-
},
83-
timestamp: '2025-05-10T10:15:30.123Z',
84-
}
85-
86-
if (includeRawEmail) {
87-
return {
88-
...baseExample,
89-
rawEmail: {
90-
id: '18e0ffabd5b5a0f4',
91-
threadId: '18e0ffabd5b5a0f4',
92-
labelIds: ['INBOX', 'IMPORTANT'],
93-
snippet: 'Hello, Please find attached the monthly report...',
94-
historyId: '123456',
95-
internalDate: '1715337323000',
96-
payload: {
97-
partId: '',
98-
mimeType: 'multipart/mixed',
99-
filename: '',
100-
headers: [
101-
{ name: 'From', value: '[email protected]' },
102-
{ name: 'To', value: '[email protected]' },
103-
{ name: 'Subject', value: 'Monthly Report - April 2025' },
104-
{ name: 'Date', value: 'Fri, 10 May 2025 10:15:23 +0000' },
105-
{ name: 'Message-ID', value: '<[email protected]>' },
106-
],
107-
body: { size: 0 },
108-
parts: [
109-
{
110-
partId: '0',
111-
mimeType: 'text/plain',
112-
filename: '',
113-
headers: [{ name: 'Content-Type', value: 'text/plain; charset=UTF-8' }],
114-
body: {
115-
size: 85,
116-
data: 'SGVsbG8sDQoNClBsZWFzZSBmaW5kIGF0dGFjaGVkIHRoZSBtb250aGx5IHJlcG9ydA==',
117-
},
118-
},
119-
],
120-
},
121-
sizeEstimate: 4156,
122-
},
123-
}
124-
}
125-
126-
return baseExample
127-
}
128-
12956
interface GmailConfigProps {
13057
selectedLabels: string[]
13158
setSelectedLabels: (labels: string[]) => void
@@ -364,17 +291,6 @@ export function GmailConfig({
364291
</div>
365292
</div>
366293
</ConfigSection>
367-
368-
<Notice
369-
variant='default'
370-
className='border-slate-200 bg-white dark:border-border dark:bg-background'
371-
icon={<GmailIcon className='mt-0.5 mr-3.5 h-5 w-5 flex-shrink-0 text-red-500' />}
372-
title='Gmail Event Payload Example'
373-
>
374-
<div className='overflow-wrap-anywhere mt-2 whitespace-normal break-normal font-mono text-sm'>
375-
<JSONView data={getExampleEmailEvent(includeRawEmail)} />
376-
</div>
377-
</Notice>
378294
</div>
379295
)
380296
}

apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel-new/components/editor/components/sub-block/components/webhook/components/providers/outlook.tsx

Lines changed: 0 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
import { useEffect, useState } from 'react'
22
import { Info } from 'lucide-react'
33
import { Tooltip } from '@/components/emcn'
4-
import { OutlookIcon } from '@/components/icons'
54
import {
65
Badge,
76
Button,
@@ -16,7 +15,6 @@ import {
1615
Skeleton,
1716
} from '@/components/ui'
1817
import { createLogger } from '@/lib/logs/console/logger'
19-
import { JSONView } from '@/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/console/components'
2018
import { ConfigSection } from '@/app/workspace/[workspaceId]/w/[workflowId]/components/panel-new/components/editor/components/sub-block/components/webhook/components'
2119

2220
const logger = createLogger('OutlookConfig')
@@ -40,70 +38,6 @@ const TOOLTIPS = {
4038
}
4139

4240
// Generate example payload for Outlook
43-
const generateOutlookExamplePayload = (includeRawEmail: boolean) => {
44-
const baseExample: any = {
45-
email: {
46-
id: 'AAMkAGVmMDEzMTM4LTZmYWUtNDdkNC1hMDZiLTU1OGY5OTZhYmY4OABGAAAAAAAiQ8W967B7TKBjgx9rVEURBwAiIsqMbYjsT5e-T4KzowKTAAAAAAEMAAAiIsqMbYjsT5e-T4KzowKTAAAYbvZDAAA=',
47-
conversationId:
48-
'AAQkAGVmMDEzMTM4LTZmYWUtNDdkNC1hMDZiLTU1OGY5OTZhYmY4OAAQAOH_y8jLzUGIn-HVkHUBrEE=',
49-
subject: 'Monthly Report - January 2024',
50-
51-
52-
cc: '',
53-
date: '2024-01-15T10:30:00Z',
54-
bodyText: 'Hello, Please find attached the monthly report for January 2024.',
55-
bodyHtml: '<p>Hello,</p><p>Please find attached the monthly report for January 2024.</p>',
56-
hasAttachments: true,
57-
isRead: false,
58-
folderId: 'inbox',
59-
},
60-
timestamp: '2024-01-15T10:30:15.123Z',
61-
}
62-
63-
if (includeRawEmail) {
64-
baseExample.rawEmail = {
65-
id: 'AAMkAGVmMDEzMTM4LTZmYWUtNDdkNC1hMDZiLTU1OGY5OTZhYmY4OABGAAAAAAAiQ8W967B7TKBjgx9rVEURBwAiIsqMbYjsT5e-T4KzowKTAAAAAAEMAAAiIsqMbYjsT5e-T4KzowKTAAAYbvZDAAA=',
66-
conversationId:
67-
'AAQkAGVmMDEzMTM4LTZmYWUtNDdkNC1hMDZiLTU1OGY5OTZhYmY4OAAQAOH_y8jLzUGIn-HVkHUBrEE=',
68-
subject: 'Monthly Report - January 2024',
69-
bodyPreview: 'Hello, Please find attached the monthly report for January 2024.',
70-
body: {
71-
contentType: 'html',
72-
content: '<p>Hello,</p><p>Please find attached the monthly report for January 2024.</p>',
73-
},
74-
from: {
75-
emailAddress: {
76-
name: 'John Doe',
77-
address: '[email protected]',
78-
},
79-
},
80-
toRecipients: [
81-
{
82-
emailAddress: {
83-
name: 'Jane Smith',
84-
address: '[email protected]',
85-
},
86-
},
87-
],
88-
ccRecipients: [],
89-
bccRecipients: [],
90-
receivedDateTime: '2024-01-15T10:30:00Z',
91-
sentDateTime: '2024-01-15T10:29:45Z',
92-
hasAttachments: true,
93-
isRead: false,
94-
isDraft: false,
95-
importance: 'normal',
96-
parentFolderId: 'inbox',
97-
internetMessageId: '<[email protected]>',
98-
webLink: 'https://outlook.office365.com/owa/?ItemID=...',
99-
createdDateTime: '2024-01-15T10:30:00Z',
100-
lastModifiedDateTime: '2024-01-15T10:30:15Z',
101-
changeKey: 'CQAAABYAAAAiIsqMbYjsT5e-T4KzowKTAAAYbvZE',
102-
}
103-
}
104-
105-
return baseExample
106-
}
10741

10842
interface OutlookConfigProps {
10943
selectedLabels: string[]
@@ -368,16 +302,6 @@ export function OutlookConfig({
368302
</div>
369303
</div>
370304
</ConfigSection>
371-
372-
<ConfigSection>
373-
<div className='mb-3 flex items-center gap-2'>
374-
<OutlookIcon className='h-4 w-4' />
375-
<h3 className='font-medium text-sm'>Outlook Event Payload Example</h3>
376-
</div>
377-
<div className='rounded-md border bg-muted/50 p-3'>
378-
<JSONView data={generateOutlookExamplePayload(includeRawEmail)} />
379-
</div>
380-
</ConfigSection>
381305
</div>
382306
)
383307
}

apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel-new/components/editor/components/sub-block/components/webhook/components/providers/slack.tsx

Lines changed: 0 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
import { SlackIcon } from '@/components/icons'
2-
import { Notice } from '@/components/ui'
3-
import { JSONView } from '@/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/console/components'
41
import {
52
ConfigSection,
63
InstructionsSection,
@@ -23,24 +20,6 @@ interface SlackConfigProps {
2320
webhookUrl: string
2421
}
2522

26-
const exampleEvent = JSON.stringify(
27-
{
28-
type: 'event_callback',
29-
event: {
30-
type: 'message',
31-
channel: 'C0123456789',
32-
user: 'U0123456789',
33-
text: 'Hello from Slack!',
34-
ts: '1234567890.123456',
35-
},
36-
team_id: 'T0123456789',
37-
event_id: 'Ev0123456789',
38-
event_time: 1234567890,
39-
},
40-
null,
41-
2
42-
)
43-
4423
export function SlackConfig({
4524
signingSecret,
4625
setSigningSecret,
@@ -144,20 +123,6 @@ export function SlackConfig({
144123
<li>Save changes in both Slack and here.</li>
145124
</ol>
146125
</InstructionsSection>
147-
148-
<Notice
149-
variant='default'
150-
className='border-slate-200 bg-white dark:border-border dark:bg-background'
151-
icon={
152-
<SlackIcon className='mt-0.5 mr-3.5 h-5 w-5 flex-shrink-0 text-[#611f69] dark:text-[#e01e5a]' />
153-
}
154-
title='Slack Event Payload Example'
155-
>
156-
Your workflow will receive a payload similar to this when a subscribed event occurs:
157-
<div className='overflow-wrap-anywhere mt-2 whitespace-normal break-normal font-mono text-sm'>
158-
<JSONView data={JSON.parse(exampleEvent)} />
159-
</div>
160-
</Notice>
161126
</div>
162127
)
163128
}

0 commit comments

Comments
 (0)