@walkeros/server-destination-slack 3.4.0 → 3.4.1-next-1776790594143

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/dist/dev.js CHANGED
@@ -1 +1 @@
1
- "use strict";var e,t=Object.defineProperty,a=Object.getOwnPropertyDescriptor,n=Object.getOwnPropertyNames,r=Object.prototype.hasOwnProperty,o=(e,a)=>{for(var n in a)t(e,n,{get:a[n],enumerable:!0})},s={};o(s,{examples:()=>g,schemas:()=>i}),module.exports=(e=s,((e,o,s,i)=>{if(o&&"object"==typeof o||"function"==typeof o)for(let l of n(o))r.call(e,l)||l===s||t(e,l,{get:()=>o[l],enumerable:!(i=a(o,l))||i.enumerable});return e})(t({},"__esModule",{value:!0}),e));var i={};o(i,{MappingSchema:()=>u,SettingsSchema:()=>d,mapping:()=>h,settings:()=>m});var l=require("@walkeros/core/dev"),c=require("@walkeros/core/dev"),d=c.z.object({token:c.z.string().startsWith("xoxb-").describe("Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.").optional(),webhookUrl:c.z.string().url().describe("Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.").optional(),channel:c.z.string().describe('Default Slack channel ID or name (e.g. "#alerts" or "C024BE91L"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.').optional(),text:c.z.string().describe("Default text template. Supports `${data.field}` interpolation against the walkerOS event.").optional(),blocks:c.z.array(c.z.record(c.z.string(),c.z.unknown())).describe("Default Block Kit blocks applied when no mapping override is set.").optional(),includeHeader:c.z.boolean().describe("Auto-add an event-name header block when generating default blocks. Default: true.").optional(),unfurlLinks:c.z.boolean().describe("Enable link unfurling. Default: false (cleaner for automated alerts).").optional(),unfurlMedia:c.z.boolean().describe("Enable media unfurling. Default: false.").optional(),mrkdwn:c.z.boolean().describe("Use mrkdwn formatting in text. Default: true.").optional(),threadTs:c.z.string().describe("Static thread_ts for replies (rarely set at destination level).").optional(),retryConfig:c.z.enum(["default","fiveRetriesInFiveMinutes","none"]).describe('Retry policy passed to WebClient. Default: "default".').optional()}).refine(e=>Boolean(e.token)!==Boolean(e.webhookUrl),{message:"Provide exactly one of `token` or `webhookUrl`."}),p=require("@walkeros/core/dev"),u=p.z.object({channel:p.z.string().describe("Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.").optional(),text:p.z.string().describe("Override the text template for this rule. Supports `${data.field}` interpolation.").optional(),blocks:p.z.array(p.z.record(p.z.string(),p.z.unknown())).describe("Override Block Kit blocks for this rule.").optional(),threadTs:p.z.string().describe("thread_ts for posting as a reply in a thread.").optional(),replyBroadcast:p.z.boolean().describe("Also broadcast the threaded reply back to the channel.").optional(),ephemeral:p.z.boolean().describe("Send via chat.postEphemeral. Requires `user`.").optional(),user:p.z.string().describe("Slack user ID for ephemeral or DM delivery.").optional(),dm:p.z.boolean().describe("Send as DM via conversations.open + chat.postMessage. Requires `user`.").optional()}),m=(0,l.zodToSchema)(d),h=(0,l.zodToSchema)(u),g={};o(g,{env:()=>k,step:()=>x});var k={};o(k,{push:()=>y,simulation:()=>w});var b={ok:!0,channel:"CMOCK",ts:"1700000000.000100"},f={ok:!0},v={ok:!0,channel:{id:"D-MOCK-DM"}};var y={slackClient:{chat:{postMessage:()=>Promise.resolve(b),postEphemeral:()=>Promise.resolve(f)},conversations:{open:()=>Promise.resolve(v)}},sendServer:()=>Promise.resolve({ok:!0})},w=["call:slackClient.chat.postMessage","call:slackClient.chat.postEphemeral","call:slackClient.conversations.open","call:sendServer"],x={};o(x,{defaultBlocks:()=>C,deployNotification:()=>O,ephemeralMessage:()=>S,errorAlert:()=>M,purchaseAlert:()=>E,threadedCheckoutStep:()=>D,welcomeDM:()=>_});var z=require("@walkeros/core"),E={in:(0,z.getEvent)("order complete",{timestamp:1700000100,data:{id:"ORD-500",total:299.99,currency:"EUR",product:"Pro Plan"},user:{id:"buyer-42"}}),mapping:{settings:{channel:"#sales",text:":moneybag: New order: ${data.id} - ${data.total} ${data.currency}"}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:":moneybag: New order: ORD-500 - 299.99 EUR",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},M={in:(0,z.getEvent)("error occur",{timestamp:1700000200,data:{message:"Payment gateway timeout",code:"PGW_TIMEOUT",severity:"critical"}}),mapping:{settings:{channel:"#engineering-alerts",text:":rotating_light: Error: ${data.message}"}},out:[["slackClient.chat.postMessage",{channel:"#engineering-alerts",text:":rotating_light: Error: Payment gateway timeout",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},_={in:(0,z.getEvent)("user signup",{timestamp:1700000300,data:{plan:"enterprise"},user:{id:"U-NEW-USER"}}),mapping:{settings:{dm:!0,user:"U-NEW-USER",text:":wave: Welcome aboard! You signed up for the ${data.plan} plan."}},out:[["slackClient.conversations.open",{users:"U-NEW-USER"}],["slackClient.chat.postMessage",{channel:"D-MOCK-DM",text:":wave: Welcome aboard! You signed up for the enterprise plan.",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},D={in:(0,z.getEvent)("checkout step",{timestamp:1700000400,data:{step:"payment",sessionTs:"1700000000.000050"}}),mapping:{settings:{channel:"#sales",text:"Checkout step: ${data.step}",threadTs:"1700000000.000050",replyBroadcast:!0}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:"Checkout step: payment",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,thread_ts:"1700000000.000050",reply_broadcast:!0}]]},S={in:(0,z.getEvent)("quota warning",{timestamp:1700000500,data:{remaining:5}}),mapping:{settings:{channel:"#admin",ephemeral:!0,user:"U-ADMIN-1",text:"Heads up: ${data.remaining} requests remaining"}},out:[["slackClient.chat.postEphemeral",{channel:"#admin",text:"Heads up: 5 requests remaining",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,user:"U-ADMIN-1"}]]},C={in:(0,z.getEvent)("lead submit",{timestamp:1700000600,data:{name:"Acme",email:"sales@acme.test"},source:{type:"server",id:"crm",previous_id:""}}),mapping:{settings:{channel:"#growth"}},out:[["slackClient.chat.postMessage",{channel:"#growth",text:"lead submit",blocks:[{type:"header",text:{type:"plain_text",text:"lead submit"}},{type:"section",fields:[{type:"mrkdwn",text:"*name:*\nAcme"},{type:"mrkdwn",text:"*email:*\nsales@acme.test"}]},{type:"context",elements:[{type:"mrkdwn",text:"Source: crm"}]}],unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},O={in:(0,z.getEvent)("deploy complete",{timestamp:1700000700,data:{version:"1.4.2",environment:"prod"}}),settings:{token:void 0,webhookUrl:"https://hooks.slack.com/services/T00/B00/xxx"},mapping:{settings:{text:":rocket: Deployment complete: ${data.version} to ${data.environment}"}},out:[["sendServer","https://hooks.slack.com/services/T00/B00/xxx",JSON.stringify({text:":rocket: Deployment complete: 1.4.2 to prod",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0})]]};//# sourceMappingURL=dev.js.map
1
+ "use strict";var e,t=Object.defineProperty,a=Object.getOwnPropertyDescriptor,n=Object.getOwnPropertyNames,r=Object.prototype.hasOwnProperty,o=(e,a)=>{for(var n in a)t(e,n,{get:a[n],enumerable:!0})},s={};o(s,{examples:()=>g,schemas:()=>i}),module.exports=(e=s,((e,o,s,i)=>{if(o&&"object"==typeof o||"function"==typeof o)for(let l of n(o))r.call(e,l)||l===s||t(e,l,{get:()=>o[l],enumerable:!(i=a(o,l))||i.enumerable});return e})(t({},"__esModule",{value:!0}),e));var i={};o(i,{MappingSchema:()=>u,SettingsSchema:()=>d,mapping:()=>h,settings:()=>m});var l=require("@walkeros/core/dev"),c=require("@walkeros/core/dev"),d=c.z.object({token:c.z.string().startsWith("xoxb-").describe("Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.").optional(),webhookUrl:c.z.string().url().describe("Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.").optional(),channel:c.z.string().describe('Default Slack channel ID or name (e.g. "#alerts" or "C024BE91L"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.').optional(),text:c.z.string().describe("Default text template. Supports `${data.field}` interpolation against the walkerOS event.").optional(),blocks:c.z.array(c.z.record(c.z.string(),c.z.unknown())).describe("Default Block Kit blocks applied when no mapping override is set.").optional(),includeHeader:c.z.boolean().describe("Auto-add an event-name header block when generating default blocks. Default: true.").optional(),unfurlLinks:c.z.boolean().describe("Enable link unfurling. Default: false (cleaner for automated alerts).").optional(),unfurlMedia:c.z.boolean().describe("Enable media unfurling. Default: false.").optional(),mrkdwn:c.z.boolean().describe("Use mrkdwn formatting in text. Default: true.").optional(),threadTs:c.z.string().describe("Static thread_ts for replies (rarely set at destination level).").optional(),retryConfig:c.z.enum(["default","fiveRetriesInFiveMinutes","none"]).describe('Retry policy passed to WebClient. Default: "default".').optional()}).refine(e=>Boolean(e.token)!==Boolean(e.webhookUrl),{message:"Provide exactly one of `token` or `webhookUrl`."}),p=require("@walkeros/core/dev"),u=p.z.object({channel:p.z.string().describe("Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.").optional(),text:p.z.string().describe("Override the text template for this rule. Supports `${data.field}` interpolation.").optional(),blocks:p.z.array(p.z.record(p.z.string(),p.z.unknown())).describe("Override Block Kit blocks for this rule.").optional(),threadTs:p.z.string().describe("thread_ts for posting as a reply in a thread.").optional(),replyBroadcast:p.z.boolean().describe("Also broadcast the threaded reply back to the channel.").optional(),ephemeral:p.z.boolean().describe("Send via chat.postEphemeral. Requires `user`.").optional(),user:p.z.string().describe("Slack user ID for ephemeral or DM delivery.").optional(),dm:p.z.boolean().describe("Send as DM via conversations.open + chat.postMessage. Requires `user`.").optional()}),m=(0,l.zodToSchema)(d),h=(0,l.zodToSchema)(u),g={};o(g,{env:()=>k,step:()=>x});var k={};o(k,{push:()=>y,simulation:()=>w});var b={ok:!0,channel:"CMOCK",ts:"1700000000.000100"},v={ok:!0},f={ok:!0,channel:{id:"D-MOCK-DM"}};var y={slackClient:{chat:{postMessage:()=>Promise.resolve(b),postEphemeral:()=>Promise.resolve(v)},conversations:{open:()=>Promise.resolve(f)}},sendServer:()=>Promise.resolve({ok:!0})},w=["call:slackClient.chat.postMessage","call:slackClient.chat.postEphemeral","call:slackClient.conversations.open","call:sendServer"],x={};o(x,{defaultBlocks:()=>C,deployNotification:()=>P,ephemeralMessage:()=>_,errorAlert:()=>M,purchaseAlert:()=>E,threadedCheckoutStep:()=>D,welcomeDM:()=>S});var z=require("@walkeros/core"),E={title:"Purchase alert",description:"A completed order posts a templated message to a sales channel via the Slack Web API.",in:(0,z.getEvent)("order complete",{timestamp:1700000100,data:{id:"ORD-500",total:299.99,currency:"EUR",product:"Pro Plan"},user:{id:"buyer-42"}}),mapping:{settings:{channel:"#sales",text:":moneybag: New order: ${data.id} - ${data.total} ${data.currency}"}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:":moneybag: New order: ORD-500 - 299.99 EUR",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},M={title:"Error alert",description:"An error event posts a critical alert to an engineering channel using a mapping-level channel override.",in:(0,z.getEvent)("error occur",{timestamp:1700000200,data:{message:"Payment gateway timeout",code:"PGW_TIMEOUT",severity:"critical"}}),mapping:{settings:{channel:"#engineering-alerts",text:":rotating_light: Error: ${data.message}"}},out:[["slackClient.chat.postMessage",{channel:"#engineering-alerts",text:":rotating_light: Error: Payment gateway timeout",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},S={title:"Welcome DM",description:"A user signup opens a Slack DM channel and posts a welcome message with the selected plan.",in:(0,z.getEvent)("user signup",{timestamp:1700000300,data:{plan:"enterprise"},user:{id:"U-NEW-USER"}}),mapping:{settings:{dm:!0,user:"U-NEW-USER",text:":wave: Welcome aboard! You signed up for the ${data.plan} plan."}},out:[["slackClient.conversations.open",{users:"U-NEW-USER"}],["slackClient.chat.postMessage",{channel:"D-MOCK-DM",text:":wave: Welcome aboard! You signed up for the enterprise plan.",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},D={title:"Threaded reply",description:"A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.",in:(0,z.getEvent)("checkout step",{timestamp:1700000400,data:{step:"payment",sessionTs:"1700000000.000050"}}),mapping:{settings:{channel:"#sales",text:"Checkout step: ${data.step}",threadTs:"1700000000.000050",replyBroadcast:!0}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:"Checkout step: payment",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,thread_ts:"1700000000.000050",reply_broadcast:!0}]]},_={title:"Ephemeral message",description:"A quota warning posts an ephemeral Slack message visible only to a target admin user.",in:(0,z.getEvent)("quota warning",{timestamp:1700000500,data:{remaining:5}}),mapping:{settings:{channel:"#admin",ephemeral:!0,user:"U-ADMIN-1",text:"Heads up: ${data.remaining} requests remaining"}},out:[["slackClient.chat.postEphemeral",{channel:"#admin",text:"Heads up: 5 requests remaining",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,user:"U-ADMIN-1"}]]},C={title:"Default blocks",description:"With no custom text the destination auto-generates a Block Kit message from event data and source.",in:(0,z.getEvent)("lead submit",{timestamp:1700000600,data:{name:"Acme",email:"sales@acme.test"},source:{type:"server",id:"crm",previous_id:""}}),mapping:{settings:{channel:"#growth"}},out:[["slackClient.chat.postMessage",{channel:"#growth",text:"lead submit",blocks:[{type:"header",text:{type:"plain_text",text:"lead submit"}},{type:"section",fields:[{type:"mrkdwn",text:"*name:*\nAcme"},{type:"mrkdwn",text:"*email:*\nsales@acme.test"}]},{type:"context",elements:[{type:"mrkdwn",text:"Source: crm"}]}],unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},P={title:"Webhook deploy",description:"Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.",in:(0,z.getEvent)("deploy complete",{timestamp:1700000700,data:{version:"1.4.2",environment:"prod"}}),settings:{token:void 0,webhookUrl:"https://hooks.slack.com/services/T00/B00/xxx"},mapping:{settings:{text:":rocket: Deployment complete: ${data.version} to ${data.environment}"}},out:[["sendServer","https://hooks.slack.com/services/T00/B00/xxx",JSON.stringify({text:":rocket: Deployment complete: 1.4.2 to prod",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0})]]};//# sourceMappingURL=dev.js.map
package/dist/dev.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/dev.ts","../src/schemas/index.ts","../src/schemas/settings.ts","../src/schemas/mapping.ts","../src/examples/index.ts","../src/examples/env.ts","../src/examples/step.ts"],"sourcesContent":["export * as schemas from './schemas';\nexport * as examples from './examples';\n","import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z\n .object({\n token: z\n .string()\n .startsWith('xoxb-')\n .describe(\n 'Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.',\n )\n .optional(),\n webhookUrl: z\n .string()\n .url()\n .describe(\n 'Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.',\n )\n .optional(),\n channel: z\n .string()\n .describe(\n 'Default Slack channel ID or name (e.g. \"#alerts\" or \"C024BE91L\"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Default text template. Supports `${data.field}` interpolation against the walkerOS event.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe(\n 'Default Block Kit blocks applied when no mapping override is set.',\n )\n .optional(),\n includeHeader: z\n .boolean()\n .describe(\n 'Auto-add an event-name header block when generating default blocks. Default: true.',\n )\n .optional(),\n unfurlLinks: z\n .boolean()\n .describe(\n 'Enable link unfurling. Default: false (cleaner for automated alerts).',\n )\n .optional(),\n unfurlMedia: z\n .boolean()\n .describe('Enable media unfurling. Default: false.')\n .optional(),\n mrkdwn: z\n .boolean()\n .describe('Use mrkdwn formatting in text. Default: true.')\n .optional(),\n threadTs: z\n .string()\n .describe(\n 'Static thread_ts for replies (rarely set at destination level).',\n )\n .optional(),\n retryConfig: z\n .enum(['default', 'fiveRetriesInFiveMinutes', 'none'])\n .describe('Retry policy passed to WebClient. Default: \"default\".')\n .optional(),\n })\n .refine((v) => Boolean(v.token) !== Boolean(v.webhookUrl), {\n message: 'Provide exactly one of `token` or `webhookUrl`.',\n });\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\nexport const MappingSchema = z.object({\n channel: z\n .string()\n .describe(\n 'Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Override the text template for this rule. Supports `${data.field}` interpolation.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe('Override Block Kit blocks for this rule.')\n .optional(),\n threadTs: z\n .string()\n .describe('thread_ts for posting as a reply in a thread.')\n .optional(),\n replyBroadcast: z\n .boolean()\n .describe('Also broadcast the threaded reply back to the channel.')\n .optional(),\n ephemeral: z\n .boolean()\n .describe('Send via chat.postEphemeral. Requires `user`.')\n .optional(),\n user: z\n .string()\n .describe('Slack user ID for ephemeral or DM delivery.')\n .optional(),\n dm: z\n .boolean()\n .describe(\n 'Send as DM via conversations.open + chat.postMessage. Requires `user`.',\n )\n .optional(),\n});\n\nexport type Mapping = z.infer<typeof MappingSchema>;\n","export * as env from './env';\nexport * as step from './step';\n","import type { Env, SlackClientMock } from '../types';\n\nconst okMessageResponse = {\n ok: true as const,\n channel: 'CMOCK',\n ts: '1700000000.000100',\n};\n\nconst okEphemeralResponse = { ok: true as const };\n\nconst okOpenResponse = {\n ok: true as const,\n channel: { id: 'D-MOCK-DM' },\n};\n\nfunction createMockClient(): SlackClientMock {\n return {\n chat: {\n postMessage: () => Promise.resolve(okMessageResponse as never),\n postEphemeral: () => Promise.resolve(okEphemeralResponse as never),\n },\n conversations: {\n open: () => Promise.resolve(okOpenResponse as never),\n },\n };\n}\n\nexport const push: Env = {\n slackClient: createMockClient(),\n sendServer: (() =>\n Promise.resolve({ ok: true } as never)) as Env['sendServer'],\n};\n\nexport const simulation = [\n 'call:slackClient.chat.postMessage',\n 'call:slackClient.chat.postEphemeral',\n 'call:slackClient.conversations.open',\n 'call:sendServer',\n];\n","import type { Flow } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\nimport type { Settings } from '../types';\n\n/**\n * Extended step example that may carry destination-level settings overrides.\n */\nexport type SlackStepExample = Flow.StepExample & {\n settings?: Partial<Settings>;\n};\n\n/**\n * Slack server destination operates in two modes:\n *\n * 1. Web API mode — calls the injected `env.slackClient` SDK methods\n * (`chat.postMessage`, `chat.postEphemeral`, `conversations.open`).\n * Captured as `[callable, args]` with dotted callable names such as\n * `'slackClient.chat.postMessage'`.\n *\n * 2. Webhook mode — calls `env.sendServer(url, JSON.stringify(body))`.\n * Captured as `['sendServer', url, bodyAsString]` where `bodyAsString`\n * is the already-stringified JSON body. Key insertion order in the\n * source object matters for string equality.\n *\n * A single push may emit multiple calls (e.g. a DM opens a conversation\n * then posts to the returned channel id), so every `out` is wrapped as\n * `[[callable, ...args], ...]`.\n */\n\n/**\n * Purchase notification -- Web API mode, channel from mapping override,\n * text template interpolated against event.data.\n */\nexport const purchaseAlert: SlackStepExample = {\n in: getEvent('order complete', {\n timestamp: 1700000100,\n data: {\n id: 'ORD-500',\n total: 299.99,\n currency: 'EUR',\n product: 'Pro Plan',\n },\n user: { id: 'buyer-42' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: ':moneybag: New order: ${data.id} - ${data.total} ${data.currency}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: ':moneybag: New order: ORD-500 - 299.99 EUR',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Error alert -- routes to a different channel via mapping override.\n */\nexport const errorAlert: SlackStepExample = {\n in: getEvent('error occur', {\n timestamp: 1700000200,\n data: {\n message: 'Payment gateway timeout',\n code: 'PGW_TIMEOUT',\n severity: 'critical',\n },\n }),\n mapping: {\n settings: {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: ${data.message}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: Payment gateway timeout',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Welcome DM -- conversations.open(users) -> chat.postMessage(channel: D-id).\n */\nexport const welcomeDM: SlackStepExample = {\n in: getEvent('user signup', {\n timestamp: 1700000300,\n data: { plan: 'enterprise' },\n user: { id: 'U-NEW-USER' },\n }),\n mapping: {\n settings: {\n dm: true,\n user: 'U-NEW-USER',\n text: ':wave: Welcome aboard! You signed up for the ${data.plan} plan.',\n },\n },\n out: [\n ['slackClient.conversations.open', { users: 'U-NEW-USER' }],\n [\n 'slackClient.chat.postMessage',\n {\n channel: 'D-MOCK-DM',\n text: ':wave: Welcome aboard! You signed up for the enterprise plan.',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Threaded checkout step -- thread_ts override puts the reply into a thread.\n */\nexport const threadedCheckoutStep: SlackStepExample = {\n in: getEvent('checkout step', {\n timestamp: 1700000400,\n data: { step: 'payment', sessionTs: '1700000000.000050' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: 'Checkout step: ${data.step}',\n threadTs: '1700000000.000050',\n replyBroadcast: true,\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: 'Checkout step: payment',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n thread_ts: '1700000000.000050',\n reply_broadcast: true,\n },\n ],\n ],\n};\n\n/**\n * Ephemeral message -- visible to one user in the target channel.\n */\nexport const ephemeralMessage: SlackStepExample = {\n in: getEvent('quota warning', {\n timestamp: 1700000500,\n data: { remaining: 5 },\n }),\n mapping: {\n settings: {\n channel: '#admin',\n ephemeral: true,\n user: 'U-ADMIN-1',\n text: 'Heads up: ${data.remaining} requests remaining',\n },\n },\n out: [\n [\n 'slackClient.chat.postEphemeral',\n {\n channel: '#admin',\n text: 'Heads up: 5 requests remaining',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n user: 'U-ADMIN-1',\n },\n ],\n ],\n};\n\n/**\n * Default blocks -- no custom text/blocks, destination auto-generates a\n * Block Kit message from the event data.\n */\nexport const defaultBlocks: SlackStepExample = {\n in: getEvent('lead submit', {\n timestamp: 1700000600,\n data: { name: 'Acme', email: 'sales@acme.test' },\n source: { type: 'server', id: 'crm', previous_id: '' },\n }),\n mapping: {\n settings: {\n channel: '#growth',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#growth',\n text: 'lead submit',\n blocks: [\n {\n type: 'header',\n text: { type: 'plain_text', text: 'lead submit' },\n },\n {\n type: 'section',\n fields: [\n { type: 'mrkdwn', text: '*name:*\\nAcme' },\n { type: 'mrkdwn', text: '*email:*\\nsales@acme.test' },\n ],\n },\n {\n type: 'context',\n elements: [{ type: 'mrkdwn', text: 'Source: crm' }],\n },\n ],\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Webhook mode -- no token, just webhookUrl. The destination calls\n * `env.sendServer(url, JSON.stringify(body))`. Channel is baked into the\n * URL by Slack.\n */\nexport const deployNotification: SlackStepExample = {\n in: getEvent('deploy complete', {\n timestamp: 1700000700,\n data: { version: '1.4.2', environment: 'prod' },\n }),\n settings: {\n token: undefined,\n webhookUrl: 'https://hooks.slack.com/services/T00/B00/xxx',\n },\n mapping: {\n settings: {\n text: ':rocket: Deployment complete: ${data.version} to ${data.environment}',\n },\n },\n out: [\n [\n 'sendServer',\n 'https://hooks.slack.com/services/T00/B00/xxx',\n JSON.stringify({\n text: ':rocket: Deployment complete: 1.4.2 to prod',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n }),\n ],\n ],\n};\n"],"mappings":"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","names":["import_dev","import_dev"]}
1
+ {"version":3,"sources":["../src/dev.ts","../src/schemas/index.ts","../src/schemas/settings.ts","../src/schemas/mapping.ts","../src/examples/index.ts","../src/examples/env.ts","../src/examples/step.ts"],"sourcesContent":["export * as schemas from './schemas';\nexport * as examples from './examples';\n","import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z\n .object({\n token: z\n .string()\n .startsWith('xoxb-')\n .describe(\n 'Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.',\n )\n .optional(),\n webhookUrl: z\n .string()\n .url()\n .describe(\n 'Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.',\n )\n .optional(),\n channel: z\n .string()\n .describe(\n 'Default Slack channel ID or name (e.g. \"#alerts\" or \"C024BE91L\"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Default text template. Supports `${data.field}` interpolation against the walkerOS event.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe(\n 'Default Block Kit blocks applied when no mapping override is set.',\n )\n .optional(),\n includeHeader: z\n .boolean()\n .describe(\n 'Auto-add an event-name header block when generating default blocks. Default: true.',\n )\n .optional(),\n unfurlLinks: z\n .boolean()\n .describe(\n 'Enable link unfurling. Default: false (cleaner for automated alerts).',\n )\n .optional(),\n unfurlMedia: z\n .boolean()\n .describe('Enable media unfurling. Default: false.')\n .optional(),\n mrkdwn: z\n .boolean()\n .describe('Use mrkdwn formatting in text. Default: true.')\n .optional(),\n threadTs: z\n .string()\n .describe(\n 'Static thread_ts for replies (rarely set at destination level).',\n )\n .optional(),\n retryConfig: z\n .enum(['default', 'fiveRetriesInFiveMinutes', 'none'])\n .describe('Retry policy passed to WebClient. Default: \"default\".')\n .optional(),\n })\n .refine((v) => Boolean(v.token) !== Boolean(v.webhookUrl), {\n message: 'Provide exactly one of `token` or `webhookUrl`.',\n });\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\nexport const MappingSchema = z.object({\n channel: z\n .string()\n .describe(\n 'Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Override the text template for this rule. Supports `${data.field}` interpolation.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe('Override Block Kit blocks for this rule.')\n .optional(),\n threadTs: z\n .string()\n .describe('thread_ts for posting as a reply in a thread.')\n .optional(),\n replyBroadcast: z\n .boolean()\n .describe('Also broadcast the threaded reply back to the channel.')\n .optional(),\n ephemeral: z\n .boolean()\n .describe('Send via chat.postEphemeral. Requires `user`.')\n .optional(),\n user: z\n .string()\n .describe('Slack user ID for ephemeral or DM delivery.')\n .optional(),\n dm: z\n .boolean()\n .describe(\n 'Send as DM via conversations.open + chat.postMessage. Requires `user`.',\n )\n .optional(),\n});\n\nexport type Mapping = z.infer<typeof MappingSchema>;\n","export * as env from './env';\nexport * as step from './step';\n","import type { Env, SlackClientMock } from '../types';\n\nconst okMessageResponse = {\n ok: true as const,\n channel: 'CMOCK',\n ts: '1700000000.000100',\n};\n\nconst okEphemeralResponse = { ok: true as const };\n\nconst okOpenResponse = {\n ok: true as const,\n channel: { id: 'D-MOCK-DM' },\n};\n\nfunction createMockClient(): SlackClientMock {\n return {\n chat: {\n postMessage: () => Promise.resolve(okMessageResponse as never),\n postEphemeral: () => Promise.resolve(okEphemeralResponse as never),\n },\n conversations: {\n open: () => Promise.resolve(okOpenResponse as never),\n },\n };\n}\n\nexport const push: Env = {\n slackClient: createMockClient(),\n sendServer: (() =>\n Promise.resolve({ ok: true } as never)) as Env['sendServer'],\n};\n\nexport const simulation = [\n 'call:slackClient.chat.postMessage',\n 'call:slackClient.chat.postEphemeral',\n 'call:slackClient.conversations.open',\n 'call:sendServer',\n];\n","import type { Flow } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\nimport type { Settings } from '../types';\n\n/**\n * Extended step example that may carry destination-level settings overrides.\n */\nexport type SlackStepExample = Flow.StepExample & {\n settings?: Partial<Settings>;\n};\n\n/**\n * Slack server destination operates in two modes:\n *\n * 1. Web API mode — calls the injected `env.slackClient` SDK methods\n * (`chat.postMessage`, `chat.postEphemeral`, `conversations.open`).\n * Captured as `[callable, args]` with dotted callable names such as\n * `'slackClient.chat.postMessage'`.\n *\n * 2. Webhook mode — calls `env.sendServer(url, JSON.stringify(body))`.\n * Captured as `['sendServer', url, bodyAsString]` where `bodyAsString`\n * is the already-stringified JSON body. Key insertion order in the\n * source object matters for string equality.\n *\n * A single push may emit multiple calls (e.g. a DM opens a conversation\n * then posts to the returned channel id), so every `out` is wrapped as\n * `[[callable, ...args], ...]`.\n */\n\n/**\n * Purchase notification -- Web API mode, channel from mapping override,\n * text template interpolated against event.data.\n */\nexport const purchaseAlert: SlackStepExample = {\n title: 'Purchase alert',\n description:\n 'A completed order posts a templated message to a sales channel via the Slack Web API.',\n in: getEvent('order complete', {\n timestamp: 1700000100,\n data: {\n id: 'ORD-500',\n total: 299.99,\n currency: 'EUR',\n product: 'Pro Plan',\n },\n user: { id: 'buyer-42' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: ':moneybag: New order: ${data.id} - ${data.total} ${data.currency}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: ':moneybag: New order: ORD-500 - 299.99 EUR',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Error alert -- routes to a different channel via mapping override.\n */\nexport const errorAlert: SlackStepExample = {\n title: 'Error alert',\n description:\n 'An error event posts a critical alert to an engineering channel using a mapping-level channel override.',\n in: getEvent('error occur', {\n timestamp: 1700000200,\n data: {\n message: 'Payment gateway timeout',\n code: 'PGW_TIMEOUT',\n severity: 'critical',\n },\n }),\n mapping: {\n settings: {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: ${data.message}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: Payment gateway timeout',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Welcome DM -- conversations.open(users) -> chat.postMessage(channel: D-id).\n */\nexport const welcomeDM: SlackStepExample = {\n title: 'Welcome DM',\n description:\n 'A user signup opens a Slack DM channel and posts a welcome message with the selected plan.',\n in: getEvent('user signup', {\n timestamp: 1700000300,\n data: { plan: 'enterprise' },\n user: { id: 'U-NEW-USER' },\n }),\n mapping: {\n settings: {\n dm: true,\n user: 'U-NEW-USER',\n text: ':wave: Welcome aboard! You signed up for the ${data.plan} plan.',\n },\n },\n out: [\n ['slackClient.conversations.open', { users: 'U-NEW-USER' }],\n [\n 'slackClient.chat.postMessage',\n {\n channel: 'D-MOCK-DM',\n text: ':wave: Welcome aboard! You signed up for the enterprise plan.',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Threaded checkout step -- thread_ts override puts the reply into a thread.\n */\nexport const threadedCheckoutStep: SlackStepExample = {\n title: 'Threaded reply',\n description:\n 'A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.',\n in: getEvent('checkout step', {\n timestamp: 1700000400,\n data: { step: 'payment', sessionTs: '1700000000.000050' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: 'Checkout step: ${data.step}',\n threadTs: '1700000000.000050',\n replyBroadcast: true,\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: 'Checkout step: payment',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n thread_ts: '1700000000.000050',\n reply_broadcast: true,\n },\n ],\n ],\n};\n\n/**\n * Ephemeral message -- visible to one user in the target channel.\n */\nexport const ephemeralMessage: SlackStepExample = {\n title: 'Ephemeral message',\n description:\n 'A quota warning posts an ephemeral Slack message visible only to a target admin user.',\n in: getEvent('quota warning', {\n timestamp: 1700000500,\n data: { remaining: 5 },\n }),\n mapping: {\n settings: {\n channel: '#admin',\n ephemeral: true,\n user: 'U-ADMIN-1',\n text: 'Heads up: ${data.remaining} requests remaining',\n },\n },\n out: [\n [\n 'slackClient.chat.postEphemeral',\n {\n channel: '#admin',\n text: 'Heads up: 5 requests remaining',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n user: 'U-ADMIN-1',\n },\n ],\n ],\n};\n\n/**\n * Default blocks -- no custom text/blocks, destination auto-generates a\n * Block Kit message from the event data.\n */\nexport const defaultBlocks: SlackStepExample = {\n title: 'Default blocks',\n description:\n 'With no custom text the destination auto-generates a Block Kit message from event data and source.',\n in: getEvent('lead submit', {\n timestamp: 1700000600,\n data: { name: 'Acme', email: 'sales@acme.test' },\n source: { type: 'server', id: 'crm', previous_id: '' },\n }),\n mapping: {\n settings: {\n channel: '#growth',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#growth',\n text: 'lead submit',\n blocks: [\n {\n type: 'header',\n text: { type: 'plain_text', text: 'lead submit' },\n },\n {\n type: 'section',\n fields: [\n { type: 'mrkdwn', text: '*name:*\\nAcme' },\n { type: 'mrkdwn', text: '*email:*\\nsales@acme.test' },\n ],\n },\n {\n type: 'context',\n elements: [{ type: 'mrkdwn', text: 'Source: crm' }],\n },\n ],\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Webhook mode -- no token, just webhookUrl. The destination calls\n * `env.sendServer(url, JSON.stringify(body))`. Channel is baked into the\n * URL by Slack.\n */\nexport const deployNotification: SlackStepExample = {\n title: 'Webhook deploy',\n description:\n 'Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.',\n in: getEvent('deploy complete', {\n timestamp: 1700000700,\n data: { version: '1.4.2', environment: 'prod' },\n }),\n settings: {\n token: undefined,\n webhookUrl: 'https://hooks.slack.com/services/T00/B00/xxx',\n },\n mapping: {\n settings: {\n text: ':rocket: Deployment complete: ${data.version} to ${data.environment}',\n },\n },\n out: [\n [\n 'sendServer',\n 'https://hooks.slack.com/services/T00/B00/xxx',\n JSON.stringify({\n text: ':rocket: Deployment complete: 1.4.2 to prod',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n }),\n ],\n ],\n};\n"],"mappings":"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","names":["import_dev","import_dev"]}
package/dist/dev.mjs CHANGED
@@ -1 +1 @@
1
- var e=Object.defineProperty,t=(t,a)=>{for(var n in a)e(t,n,{get:a[n],enumerable:!0})},a={};t(a,{MappingSchema:()=>i,SettingsSchema:()=>o,mapping:()=>c,settings:()=>l});import{zodToSchema as n}from"@walkeros/core/dev";import{z as r}from"@walkeros/core/dev";var o=r.object({token:r.string().startsWith("xoxb-").describe("Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.").optional(),webhookUrl:r.string().url().describe("Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.").optional(),channel:r.string().describe('Default Slack channel ID or name (e.g. "#alerts" or "C024BE91L"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.').optional(),text:r.string().describe("Default text template. Supports `${data.field}` interpolation against the walkerOS event.").optional(),blocks:r.array(r.record(r.string(),r.unknown())).describe("Default Block Kit blocks applied when no mapping override is set.").optional(),includeHeader:r.boolean().describe("Auto-add an event-name header block when generating default blocks. Default: true.").optional(),unfurlLinks:r.boolean().describe("Enable link unfurling. Default: false (cleaner for automated alerts).").optional(),unfurlMedia:r.boolean().describe("Enable media unfurling. Default: false.").optional(),mrkdwn:r.boolean().describe("Use mrkdwn formatting in text. Default: true.").optional(),threadTs:r.string().describe("Static thread_ts for replies (rarely set at destination level).").optional(),retryConfig:r.enum(["default","fiveRetriesInFiveMinutes","none"]).describe('Retry policy passed to WebClient. Default: "default".').optional()}).refine(e=>Boolean(e.token)!==Boolean(e.webhookUrl),{message:"Provide exactly one of `token` or `webhookUrl`."});import{z as s}from"@walkeros/core/dev";var i=s.object({channel:s.string().describe("Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.").optional(),text:s.string().describe("Override the text template for this rule. Supports `${data.field}` interpolation.").optional(),blocks:s.array(s.record(s.string(),s.unknown())).describe("Override Block Kit blocks for this rule.").optional(),threadTs:s.string().describe("thread_ts for posting as a reply in a thread.").optional(),replyBroadcast:s.boolean().describe("Also broadcast the threaded reply back to the channel.").optional(),ephemeral:s.boolean().describe("Send via chat.postEphemeral. Requires `user`.").optional(),user:s.string().describe("Slack user ID for ephemeral or DM delivery.").optional(),dm:s.boolean().describe("Send as DM via conversations.open + chat.postMessage. Requires `user`.").optional()}),l=n(o),c=n(i),d={};t(d,{env:()=>p,step:()=>b});var p={};t(p,{push:()=>k,simulation:()=>g});var m={ok:!0,channel:"CMOCK",ts:"1700000000.000100"},u={ok:!0},h={ok:!0,channel:{id:"D-MOCK-DM"}};var k={slackClient:{chat:{postMessage:()=>Promise.resolve(m),postEphemeral:()=>Promise.resolve(u)},conversations:{open:()=>Promise.resolve(h)}},sendServer:()=>Promise.resolve({ok:!0})},g=["call:slackClient.chat.postMessage","call:slackClient.chat.postEphemeral","call:slackClient.conversations.open","call:sendServer"],b={};t(b,{defaultBlocks:()=>D,deployNotification:()=>_,ephemeralMessage:()=>M,errorAlert:()=>y,purchaseAlert:()=>v,threadedCheckoutStep:()=>x,welcomeDM:()=>w});import{getEvent as f}from"@walkeros/core";var v={in:f("order complete",{timestamp:1700000100,data:{id:"ORD-500",total:299.99,currency:"EUR",product:"Pro Plan"},user:{id:"buyer-42"}}),mapping:{settings:{channel:"#sales",text:":moneybag: New order: ${data.id} - ${data.total} ${data.currency}"}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:":moneybag: New order: ORD-500 - 299.99 EUR",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},y={in:f("error occur",{timestamp:1700000200,data:{message:"Payment gateway timeout",code:"PGW_TIMEOUT",severity:"critical"}}),mapping:{settings:{channel:"#engineering-alerts",text:":rotating_light: Error: ${data.message}"}},out:[["slackClient.chat.postMessage",{channel:"#engineering-alerts",text:":rotating_light: Error: Payment gateway timeout",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},w={in:f("user signup",{timestamp:1700000300,data:{plan:"enterprise"},user:{id:"U-NEW-USER"}}),mapping:{settings:{dm:!0,user:"U-NEW-USER",text:":wave: Welcome aboard! You signed up for the ${data.plan} plan."}},out:[["slackClient.conversations.open",{users:"U-NEW-USER"}],["slackClient.chat.postMessage",{channel:"D-MOCK-DM",text:":wave: Welcome aboard! You signed up for the enterprise plan.",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},x={in:f("checkout step",{timestamp:1700000400,data:{step:"payment",sessionTs:"1700000000.000050"}}),mapping:{settings:{channel:"#sales",text:"Checkout step: ${data.step}",threadTs:"1700000000.000050",replyBroadcast:!0}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:"Checkout step: payment",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,thread_ts:"1700000000.000050",reply_broadcast:!0}]]},M={in:f("quota warning",{timestamp:1700000500,data:{remaining:5}}),mapping:{settings:{channel:"#admin",ephemeral:!0,user:"U-ADMIN-1",text:"Heads up: ${data.remaining} requests remaining"}},out:[["slackClient.chat.postEphemeral",{channel:"#admin",text:"Heads up: 5 requests remaining",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,user:"U-ADMIN-1"}]]},D={in:f("lead submit",{timestamp:1700000600,data:{name:"Acme",email:"sales@acme.test"},source:{type:"server",id:"crm",previous_id:""}}),mapping:{settings:{channel:"#growth"}},out:[["slackClient.chat.postMessage",{channel:"#growth",text:"lead submit",blocks:[{type:"header",text:{type:"plain_text",text:"lead submit"}},{type:"section",fields:[{type:"mrkdwn",text:"*name:*\nAcme"},{type:"mrkdwn",text:"*email:*\nsales@acme.test"}]},{type:"context",elements:[{type:"mrkdwn",text:"Source: crm"}]}],unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},_={in:f("deploy complete",{timestamp:1700000700,data:{version:"1.4.2",environment:"prod"}}),settings:{token:void 0,webhookUrl:"https://hooks.slack.com/services/T00/B00/xxx"},mapping:{settings:{text:":rocket: Deployment complete: ${data.version} to ${data.environment}"}},out:[["sendServer","https://hooks.slack.com/services/T00/B00/xxx",JSON.stringify({text:":rocket: Deployment complete: 1.4.2 to prod",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0})]]};export{d as examples,a as schemas};//# sourceMappingURL=dev.mjs.map
1
+ var e=Object.defineProperty,t=(t,a)=>{for(var n in a)e(t,n,{get:a[n],enumerable:!0})},a={};t(a,{MappingSchema:()=>i,SettingsSchema:()=>r,mapping:()=>c,settings:()=>l});import{zodToSchema as n}from"@walkeros/core/dev";import{z as o}from"@walkeros/core/dev";var r=o.object({token:o.string().startsWith("xoxb-").describe("Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.").optional(),webhookUrl:o.string().url().describe("Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.").optional(),channel:o.string().describe('Default Slack channel ID or name (e.g. "#alerts" or "C024BE91L"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.').optional(),text:o.string().describe("Default text template. Supports `${data.field}` interpolation against the walkerOS event.").optional(),blocks:o.array(o.record(o.string(),o.unknown())).describe("Default Block Kit blocks applied when no mapping override is set.").optional(),includeHeader:o.boolean().describe("Auto-add an event-name header block when generating default blocks. Default: true.").optional(),unfurlLinks:o.boolean().describe("Enable link unfurling. Default: false (cleaner for automated alerts).").optional(),unfurlMedia:o.boolean().describe("Enable media unfurling. Default: false.").optional(),mrkdwn:o.boolean().describe("Use mrkdwn formatting in text. Default: true.").optional(),threadTs:o.string().describe("Static thread_ts for replies (rarely set at destination level).").optional(),retryConfig:o.enum(["default","fiveRetriesInFiveMinutes","none"]).describe('Retry policy passed to WebClient. Default: "default".').optional()}).refine(e=>Boolean(e.token)!==Boolean(e.webhookUrl),{message:"Provide exactly one of `token` or `webhookUrl`."});import{z as s}from"@walkeros/core/dev";var i=s.object({channel:s.string().describe("Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.").optional(),text:s.string().describe("Override the text template for this rule. Supports `${data.field}` interpolation.").optional(),blocks:s.array(s.record(s.string(),s.unknown())).describe("Override Block Kit blocks for this rule.").optional(),threadTs:s.string().describe("thread_ts for posting as a reply in a thread.").optional(),replyBroadcast:s.boolean().describe("Also broadcast the threaded reply back to the channel.").optional(),ephemeral:s.boolean().describe("Send via chat.postEphemeral. Requires `user`.").optional(),user:s.string().describe("Slack user ID for ephemeral or DM delivery.").optional(),dm:s.boolean().describe("Send as DM via conversations.open + chat.postMessage. Requires `user`.").optional()}),l=n(r),c=n(i),d={};t(d,{env:()=>p,step:()=>b});var p={};t(p,{push:()=>g,simulation:()=>k});var m={ok:!0,channel:"CMOCK",ts:"1700000000.000100"},u={ok:!0},h={ok:!0,channel:{id:"D-MOCK-DM"}};var g={slackClient:{chat:{postMessage:()=>Promise.resolve(m),postEphemeral:()=>Promise.resolve(u)},conversations:{open:()=>Promise.resolve(h)}},sendServer:()=>Promise.resolve({ok:!0})},k=["call:slackClient.chat.postMessage","call:slackClient.chat.postEphemeral","call:slackClient.conversations.open","call:sendServer"],b={};t(b,{defaultBlocks:()=>D,deployNotification:()=>S,ephemeralMessage:()=>M,errorAlert:()=>y,purchaseAlert:()=>v,threadedCheckoutStep:()=>x,welcomeDM:()=>w});import{getEvent as f}from"@walkeros/core";var v={title:"Purchase alert",description:"A completed order posts a templated message to a sales channel via the Slack Web API.",in:f("order complete",{timestamp:1700000100,data:{id:"ORD-500",total:299.99,currency:"EUR",product:"Pro Plan"},user:{id:"buyer-42"}}),mapping:{settings:{channel:"#sales",text:":moneybag: New order: ${data.id} - ${data.total} ${data.currency}"}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:":moneybag: New order: ORD-500 - 299.99 EUR",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},y={title:"Error alert",description:"An error event posts a critical alert to an engineering channel using a mapping-level channel override.",in:f("error occur",{timestamp:1700000200,data:{message:"Payment gateway timeout",code:"PGW_TIMEOUT",severity:"critical"}}),mapping:{settings:{channel:"#engineering-alerts",text:":rotating_light: Error: ${data.message}"}},out:[["slackClient.chat.postMessage",{channel:"#engineering-alerts",text:":rotating_light: Error: Payment gateway timeout",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},w={title:"Welcome DM",description:"A user signup opens a Slack DM channel and posts a welcome message with the selected plan.",in:f("user signup",{timestamp:1700000300,data:{plan:"enterprise"},user:{id:"U-NEW-USER"}}),mapping:{settings:{dm:!0,user:"U-NEW-USER",text:":wave: Welcome aboard! You signed up for the ${data.plan} plan."}},out:[["slackClient.conversations.open",{users:"U-NEW-USER"}],["slackClient.chat.postMessage",{channel:"D-MOCK-DM",text:":wave: Welcome aboard! You signed up for the enterprise plan.",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},x={title:"Threaded reply",description:"A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.",in:f("checkout step",{timestamp:1700000400,data:{step:"payment",sessionTs:"1700000000.000050"}}),mapping:{settings:{channel:"#sales",text:"Checkout step: ${data.step}",threadTs:"1700000000.000050",replyBroadcast:!0}},out:[["slackClient.chat.postMessage",{channel:"#sales",text:"Checkout step: payment",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,thread_ts:"1700000000.000050",reply_broadcast:!0}]]},M={title:"Ephemeral message",description:"A quota warning posts an ephemeral Slack message visible only to a target admin user.",in:f("quota warning",{timestamp:1700000500,data:{remaining:5}}),mapping:{settings:{channel:"#admin",ephemeral:!0,user:"U-ADMIN-1",text:"Heads up: ${data.remaining} requests remaining"}},out:[["slackClient.chat.postEphemeral",{channel:"#admin",text:"Heads up: 5 requests remaining",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0,user:"U-ADMIN-1"}]]},D={title:"Default blocks",description:"With no custom text the destination auto-generates a Block Kit message from event data and source.",in:f("lead submit",{timestamp:1700000600,data:{name:"Acme",email:"sales@acme.test"},source:{type:"server",id:"crm",previous_id:""}}),mapping:{settings:{channel:"#growth"}},out:[["slackClient.chat.postMessage",{channel:"#growth",text:"lead submit",blocks:[{type:"header",text:{type:"plain_text",text:"lead submit"}},{type:"section",fields:[{type:"mrkdwn",text:"*name:*\nAcme"},{type:"mrkdwn",text:"*email:*\nsales@acme.test"}]},{type:"context",elements:[{type:"mrkdwn",text:"Source: crm"}]}],unfurl_links:!1,unfurl_media:!1,mrkdwn:!0}]]},S={title:"Webhook deploy",description:"Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.",in:f("deploy complete",{timestamp:1700000700,data:{version:"1.4.2",environment:"prod"}}),settings:{token:void 0,webhookUrl:"https://hooks.slack.com/services/T00/B00/xxx"},mapping:{settings:{text:":rocket: Deployment complete: ${data.version} to ${data.environment}"}},out:[["sendServer","https://hooks.slack.com/services/T00/B00/xxx",JSON.stringify({text:":rocket: Deployment complete: 1.4.2 to prod",unfurl_links:!1,unfurl_media:!1,mrkdwn:!0})]]};export{d as examples,a as schemas};//# sourceMappingURL=dev.mjs.map
package/dist/dev.mjs.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/schemas/index.ts","../src/schemas/settings.ts","../src/schemas/mapping.ts","../src/examples/index.ts","../src/examples/env.ts","../src/examples/step.ts"],"sourcesContent":["import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z\n .object({\n token: z\n .string()\n .startsWith('xoxb-')\n .describe(\n 'Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.',\n )\n .optional(),\n webhookUrl: z\n .string()\n .url()\n .describe(\n 'Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.',\n )\n .optional(),\n channel: z\n .string()\n .describe(\n 'Default Slack channel ID or name (e.g. \"#alerts\" or \"C024BE91L\"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Default text template. Supports `${data.field}` interpolation against the walkerOS event.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe(\n 'Default Block Kit blocks applied when no mapping override is set.',\n )\n .optional(),\n includeHeader: z\n .boolean()\n .describe(\n 'Auto-add an event-name header block when generating default blocks. Default: true.',\n )\n .optional(),\n unfurlLinks: z\n .boolean()\n .describe(\n 'Enable link unfurling. Default: false (cleaner for automated alerts).',\n )\n .optional(),\n unfurlMedia: z\n .boolean()\n .describe('Enable media unfurling. Default: false.')\n .optional(),\n mrkdwn: z\n .boolean()\n .describe('Use mrkdwn formatting in text. Default: true.')\n .optional(),\n threadTs: z\n .string()\n .describe(\n 'Static thread_ts for replies (rarely set at destination level).',\n )\n .optional(),\n retryConfig: z\n .enum(['default', 'fiveRetriesInFiveMinutes', 'none'])\n .describe('Retry policy passed to WebClient. Default: \"default\".')\n .optional(),\n })\n .refine((v) => Boolean(v.token) !== Boolean(v.webhookUrl), {\n message: 'Provide exactly one of `token` or `webhookUrl`.',\n });\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\nexport const MappingSchema = z.object({\n channel: z\n .string()\n .describe(\n 'Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Override the text template for this rule. Supports `${data.field}` interpolation.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe('Override Block Kit blocks for this rule.')\n .optional(),\n threadTs: z\n .string()\n .describe('thread_ts for posting as a reply in a thread.')\n .optional(),\n replyBroadcast: z\n .boolean()\n .describe('Also broadcast the threaded reply back to the channel.')\n .optional(),\n ephemeral: z\n .boolean()\n .describe('Send via chat.postEphemeral. Requires `user`.')\n .optional(),\n user: z\n .string()\n .describe('Slack user ID for ephemeral or DM delivery.')\n .optional(),\n dm: z\n .boolean()\n .describe(\n 'Send as DM via conversations.open + chat.postMessage. Requires `user`.',\n )\n .optional(),\n});\n\nexport type Mapping = z.infer<typeof MappingSchema>;\n","export * as env from './env';\nexport * as step from './step';\n","import type { Env, SlackClientMock } from '../types';\n\nconst okMessageResponse = {\n ok: true as const,\n channel: 'CMOCK',\n ts: '1700000000.000100',\n};\n\nconst okEphemeralResponse = { ok: true as const };\n\nconst okOpenResponse = {\n ok: true as const,\n channel: { id: 'D-MOCK-DM' },\n};\n\nfunction createMockClient(): SlackClientMock {\n return {\n chat: {\n postMessage: () => Promise.resolve(okMessageResponse as never),\n postEphemeral: () => Promise.resolve(okEphemeralResponse as never),\n },\n conversations: {\n open: () => Promise.resolve(okOpenResponse as never),\n },\n };\n}\n\nexport const push: Env = {\n slackClient: createMockClient(),\n sendServer: (() =>\n Promise.resolve({ ok: true } as never)) as Env['sendServer'],\n};\n\nexport const simulation = [\n 'call:slackClient.chat.postMessage',\n 'call:slackClient.chat.postEphemeral',\n 'call:slackClient.conversations.open',\n 'call:sendServer',\n];\n","import type { Flow } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\nimport type { Settings } from '../types';\n\n/**\n * Extended step example that may carry destination-level settings overrides.\n */\nexport type SlackStepExample = Flow.StepExample & {\n settings?: Partial<Settings>;\n};\n\n/**\n * Slack server destination operates in two modes:\n *\n * 1. Web API mode — calls the injected `env.slackClient` SDK methods\n * (`chat.postMessage`, `chat.postEphemeral`, `conversations.open`).\n * Captured as `[callable, args]` with dotted callable names such as\n * `'slackClient.chat.postMessage'`.\n *\n * 2. Webhook mode — calls `env.sendServer(url, JSON.stringify(body))`.\n * Captured as `['sendServer', url, bodyAsString]` where `bodyAsString`\n * is the already-stringified JSON body. Key insertion order in the\n * source object matters for string equality.\n *\n * A single push may emit multiple calls (e.g. a DM opens a conversation\n * then posts to the returned channel id), so every `out` is wrapped as\n * `[[callable, ...args], ...]`.\n */\n\n/**\n * Purchase notification -- Web API mode, channel from mapping override,\n * text template interpolated against event.data.\n */\nexport const purchaseAlert: SlackStepExample = {\n in: getEvent('order complete', {\n timestamp: 1700000100,\n data: {\n id: 'ORD-500',\n total: 299.99,\n currency: 'EUR',\n product: 'Pro Plan',\n },\n user: { id: 'buyer-42' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: ':moneybag: New order: ${data.id} - ${data.total} ${data.currency}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: ':moneybag: New order: ORD-500 - 299.99 EUR',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Error alert -- routes to a different channel via mapping override.\n */\nexport const errorAlert: SlackStepExample = {\n in: getEvent('error occur', {\n timestamp: 1700000200,\n data: {\n message: 'Payment gateway timeout',\n code: 'PGW_TIMEOUT',\n severity: 'critical',\n },\n }),\n mapping: {\n settings: {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: ${data.message}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: Payment gateway timeout',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Welcome DM -- conversations.open(users) -> chat.postMessage(channel: D-id).\n */\nexport const welcomeDM: SlackStepExample = {\n in: getEvent('user signup', {\n timestamp: 1700000300,\n data: { plan: 'enterprise' },\n user: { id: 'U-NEW-USER' },\n }),\n mapping: {\n settings: {\n dm: true,\n user: 'U-NEW-USER',\n text: ':wave: Welcome aboard! You signed up for the ${data.plan} plan.',\n },\n },\n out: [\n ['slackClient.conversations.open', { users: 'U-NEW-USER' }],\n [\n 'slackClient.chat.postMessage',\n {\n channel: 'D-MOCK-DM',\n text: ':wave: Welcome aboard! You signed up for the enterprise plan.',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Threaded checkout step -- thread_ts override puts the reply into a thread.\n */\nexport const threadedCheckoutStep: SlackStepExample = {\n in: getEvent('checkout step', {\n timestamp: 1700000400,\n data: { step: 'payment', sessionTs: '1700000000.000050' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: 'Checkout step: ${data.step}',\n threadTs: '1700000000.000050',\n replyBroadcast: true,\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: 'Checkout step: payment',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n thread_ts: '1700000000.000050',\n reply_broadcast: true,\n },\n ],\n ],\n};\n\n/**\n * Ephemeral message -- visible to one user in the target channel.\n */\nexport const ephemeralMessage: SlackStepExample = {\n in: getEvent('quota warning', {\n timestamp: 1700000500,\n data: { remaining: 5 },\n }),\n mapping: {\n settings: {\n channel: '#admin',\n ephemeral: true,\n user: 'U-ADMIN-1',\n text: 'Heads up: ${data.remaining} requests remaining',\n },\n },\n out: [\n [\n 'slackClient.chat.postEphemeral',\n {\n channel: '#admin',\n text: 'Heads up: 5 requests remaining',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n user: 'U-ADMIN-1',\n },\n ],\n ],\n};\n\n/**\n * Default blocks -- no custom text/blocks, destination auto-generates a\n * Block Kit message from the event data.\n */\nexport const defaultBlocks: SlackStepExample = {\n in: getEvent('lead submit', {\n timestamp: 1700000600,\n data: { name: 'Acme', email: 'sales@acme.test' },\n source: { type: 'server', id: 'crm', previous_id: '' },\n }),\n mapping: {\n settings: {\n channel: '#growth',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#growth',\n text: 'lead submit',\n blocks: [\n {\n type: 'header',\n text: { type: 'plain_text', text: 'lead submit' },\n },\n {\n type: 'section',\n fields: [\n { type: 'mrkdwn', text: '*name:*\\nAcme' },\n { type: 'mrkdwn', text: '*email:*\\nsales@acme.test' },\n ],\n },\n {\n type: 'context',\n elements: [{ type: 'mrkdwn', text: 'Source: crm' }],\n },\n ],\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Webhook mode -- no token, just webhookUrl. The destination calls\n * `env.sendServer(url, JSON.stringify(body))`. Channel is baked into the\n * URL by Slack.\n */\nexport const deployNotification: SlackStepExample = {\n in: getEvent('deploy complete', {\n timestamp: 1700000700,\n data: { version: '1.4.2', environment: 'prod' },\n }),\n settings: {\n token: undefined,\n webhookUrl: 'https://hooks.slack.com/services/T00/B00/xxx',\n },\n mapping: {\n settings: {\n text: ':rocket: Deployment complete: ${data.version} to ${data.environment}',\n },\n },\n out: [\n [\n 'sendServer',\n 'https://hooks.slack.com/services/T00/B00/xxx',\n JSON.stringify({\n text: ':rocket: Deployment complete: 1.4.2 to prod',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n }),\n ],\n ],\n};\n"],"mappings":"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","names":["z"]}
1
+ {"version":3,"sources":["../src/schemas/index.ts","../src/schemas/settings.ts","../src/schemas/mapping.ts","../src/examples/index.ts","../src/examples/env.ts","../src/examples/step.ts"],"sourcesContent":["import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z\n .object({\n token: z\n .string()\n .startsWith('xoxb-')\n .describe(\n 'Slack Bot token (xoxb-...). Enables Web API mode. Mutually exclusive with webhookUrl.',\n )\n .optional(),\n webhookUrl: z\n .string()\n .url()\n .describe(\n 'Incoming Webhook URL. Enables webhook mode. Mutually exclusive with token.',\n )\n .optional(),\n channel: z\n .string()\n .describe(\n 'Default Slack channel ID or name (e.g. \"#alerts\" or \"C024BE91L\"). Required for Web API mode unless every rule supplies one. Ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Default text template. Supports `${data.field}` interpolation against the walkerOS event.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe(\n 'Default Block Kit blocks applied when no mapping override is set.',\n )\n .optional(),\n includeHeader: z\n .boolean()\n .describe(\n 'Auto-add an event-name header block when generating default blocks. Default: true.',\n )\n .optional(),\n unfurlLinks: z\n .boolean()\n .describe(\n 'Enable link unfurling. Default: false (cleaner for automated alerts).',\n )\n .optional(),\n unfurlMedia: z\n .boolean()\n .describe('Enable media unfurling. Default: false.')\n .optional(),\n mrkdwn: z\n .boolean()\n .describe('Use mrkdwn formatting in text. Default: true.')\n .optional(),\n threadTs: z\n .string()\n .describe(\n 'Static thread_ts for replies (rarely set at destination level).',\n )\n .optional(),\n retryConfig: z\n .enum(['default', 'fiveRetriesInFiveMinutes', 'none'])\n .describe('Retry policy passed to WebClient. Default: \"default\".')\n .optional(),\n })\n .refine((v) => Boolean(v.token) !== Boolean(v.webhookUrl), {\n message: 'Provide exactly one of `token` or `webhookUrl`.',\n });\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\nexport const MappingSchema = z.object({\n channel: z\n .string()\n .describe(\n 'Override the destination channel for this rule. Web API mode only -- ignored in webhook mode.',\n )\n .optional(),\n text: z\n .string()\n .describe(\n 'Override the text template for this rule. Supports `${data.field}` interpolation.',\n )\n .optional(),\n blocks: z\n .array(z.record(z.string(), z.unknown()))\n .describe('Override Block Kit blocks for this rule.')\n .optional(),\n threadTs: z\n .string()\n .describe('thread_ts for posting as a reply in a thread.')\n .optional(),\n replyBroadcast: z\n .boolean()\n .describe('Also broadcast the threaded reply back to the channel.')\n .optional(),\n ephemeral: z\n .boolean()\n .describe('Send via chat.postEphemeral. Requires `user`.')\n .optional(),\n user: z\n .string()\n .describe('Slack user ID for ephemeral or DM delivery.')\n .optional(),\n dm: z\n .boolean()\n .describe(\n 'Send as DM via conversations.open + chat.postMessage. Requires `user`.',\n )\n .optional(),\n});\n\nexport type Mapping = z.infer<typeof MappingSchema>;\n","export * as env from './env';\nexport * as step from './step';\n","import type { Env, SlackClientMock } from '../types';\n\nconst okMessageResponse = {\n ok: true as const,\n channel: 'CMOCK',\n ts: '1700000000.000100',\n};\n\nconst okEphemeralResponse = { ok: true as const };\n\nconst okOpenResponse = {\n ok: true as const,\n channel: { id: 'D-MOCK-DM' },\n};\n\nfunction createMockClient(): SlackClientMock {\n return {\n chat: {\n postMessage: () => Promise.resolve(okMessageResponse as never),\n postEphemeral: () => Promise.resolve(okEphemeralResponse as never),\n },\n conversations: {\n open: () => Promise.resolve(okOpenResponse as never),\n },\n };\n}\n\nexport const push: Env = {\n slackClient: createMockClient(),\n sendServer: (() =>\n Promise.resolve({ ok: true } as never)) as Env['sendServer'],\n};\n\nexport const simulation = [\n 'call:slackClient.chat.postMessage',\n 'call:slackClient.chat.postEphemeral',\n 'call:slackClient.conversations.open',\n 'call:sendServer',\n];\n","import type { Flow } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\nimport type { Settings } from '../types';\n\n/**\n * Extended step example that may carry destination-level settings overrides.\n */\nexport type SlackStepExample = Flow.StepExample & {\n settings?: Partial<Settings>;\n};\n\n/**\n * Slack server destination operates in two modes:\n *\n * 1. Web API mode — calls the injected `env.slackClient` SDK methods\n * (`chat.postMessage`, `chat.postEphemeral`, `conversations.open`).\n * Captured as `[callable, args]` with dotted callable names such as\n * `'slackClient.chat.postMessage'`.\n *\n * 2. Webhook mode — calls `env.sendServer(url, JSON.stringify(body))`.\n * Captured as `['sendServer', url, bodyAsString]` where `bodyAsString`\n * is the already-stringified JSON body. Key insertion order in the\n * source object matters for string equality.\n *\n * A single push may emit multiple calls (e.g. a DM opens a conversation\n * then posts to the returned channel id), so every `out` is wrapped as\n * `[[callable, ...args], ...]`.\n */\n\n/**\n * Purchase notification -- Web API mode, channel from mapping override,\n * text template interpolated against event.data.\n */\nexport const purchaseAlert: SlackStepExample = {\n title: 'Purchase alert',\n description:\n 'A completed order posts a templated message to a sales channel via the Slack Web API.',\n in: getEvent('order complete', {\n timestamp: 1700000100,\n data: {\n id: 'ORD-500',\n total: 299.99,\n currency: 'EUR',\n product: 'Pro Plan',\n },\n user: { id: 'buyer-42' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: ':moneybag: New order: ${data.id} - ${data.total} ${data.currency}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: ':moneybag: New order: ORD-500 - 299.99 EUR',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Error alert -- routes to a different channel via mapping override.\n */\nexport const errorAlert: SlackStepExample = {\n title: 'Error alert',\n description:\n 'An error event posts a critical alert to an engineering channel using a mapping-level channel override.',\n in: getEvent('error occur', {\n timestamp: 1700000200,\n data: {\n message: 'Payment gateway timeout',\n code: 'PGW_TIMEOUT',\n severity: 'critical',\n },\n }),\n mapping: {\n settings: {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: ${data.message}',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#engineering-alerts',\n text: ':rotating_light: Error: Payment gateway timeout',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Welcome DM -- conversations.open(users) -> chat.postMessage(channel: D-id).\n */\nexport const welcomeDM: SlackStepExample = {\n title: 'Welcome DM',\n description:\n 'A user signup opens a Slack DM channel and posts a welcome message with the selected plan.',\n in: getEvent('user signup', {\n timestamp: 1700000300,\n data: { plan: 'enterprise' },\n user: { id: 'U-NEW-USER' },\n }),\n mapping: {\n settings: {\n dm: true,\n user: 'U-NEW-USER',\n text: ':wave: Welcome aboard! You signed up for the ${data.plan} plan.',\n },\n },\n out: [\n ['slackClient.conversations.open', { users: 'U-NEW-USER' }],\n [\n 'slackClient.chat.postMessage',\n {\n channel: 'D-MOCK-DM',\n text: ':wave: Welcome aboard! You signed up for the enterprise plan.',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Threaded checkout step -- thread_ts override puts the reply into a thread.\n */\nexport const threadedCheckoutStep: SlackStepExample = {\n title: 'Threaded reply',\n description:\n 'A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.',\n in: getEvent('checkout step', {\n timestamp: 1700000400,\n data: { step: 'payment', sessionTs: '1700000000.000050' },\n }),\n mapping: {\n settings: {\n channel: '#sales',\n text: 'Checkout step: ${data.step}',\n threadTs: '1700000000.000050',\n replyBroadcast: true,\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#sales',\n text: 'Checkout step: payment',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n thread_ts: '1700000000.000050',\n reply_broadcast: true,\n },\n ],\n ],\n};\n\n/**\n * Ephemeral message -- visible to one user in the target channel.\n */\nexport const ephemeralMessage: SlackStepExample = {\n title: 'Ephemeral message',\n description:\n 'A quota warning posts an ephemeral Slack message visible only to a target admin user.',\n in: getEvent('quota warning', {\n timestamp: 1700000500,\n data: { remaining: 5 },\n }),\n mapping: {\n settings: {\n channel: '#admin',\n ephemeral: true,\n user: 'U-ADMIN-1',\n text: 'Heads up: ${data.remaining} requests remaining',\n },\n },\n out: [\n [\n 'slackClient.chat.postEphemeral',\n {\n channel: '#admin',\n text: 'Heads up: 5 requests remaining',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n user: 'U-ADMIN-1',\n },\n ],\n ],\n};\n\n/**\n * Default blocks -- no custom text/blocks, destination auto-generates a\n * Block Kit message from the event data.\n */\nexport const defaultBlocks: SlackStepExample = {\n title: 'Default blocks',\n description:\n 'With no custom text the destination auto-generates a Block Kit message from event data and source.',\n in: getEvent('lead submit', {\n timestamp: 1700000600,\n data: { name: 'Acme', email: 'sales@acme.test' },\n source: { type: 'server', id: 'crm', previous_id: '' },\n }),\n mapping: {\n settings: {\n channel: '#growth',\n },\n },\n out: [\n [\n 'slackClient.chat.postMessage',\n {\n channel: '#growth',\n text: 'lead submit',\n blocks: [\n {\n type: 'header',\n text: { type: 'plain_text', text: 'lead submit' },\n },\n {\n type: 'section',\n fields: [\n { type: 'mrkdwn', text: '*name:*\\nAcme' },\n { type: 'mrkdwn', text: '*email:*\\nsales@acme.test' },\n ],\n },\n {\n type: 'context',\n elements: [{ type: 'mrkdwn', text: 'Source: crm' }],\n },\n ],\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n },\n ],\n ],\n};\n\n/**\n * Webhook mode -- no token, just webhookUrl. The destination calls\n * `env.sendServer(url, JSON.stringify(body))`. Channel is baked into the\n * URL by Slack.\n */\nexport const deployNotification: SlackStepExample = {\n title: 'Webhook deploy',\n description:\n 'Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.',\n in: getEvent('deploy complete', {\n timestamp: 1700000700,\n data: { version: '1.4.2', environment: 'prod' },\n }),\n settings: {\n token: undefined,\n webhookUrl: 'https://hooks.slack.com/services/T00/B00/xxx',\n },\n mapping: {\n settings: {\n text: ':rocket: Deployment complete: ${data.version} to ${data.environment}',\n },\n },\n out: [\n [\n 'sendServer',\n 'https://hooks.slack.com/services/T00/B00/xxx',\n JSON.stringify({\n text: ':rocket: Deployment complete: 1.4.2 to prod',\n unfurl_links: false,\n unfurl_media: false,\n mrkdwn: true,\n }),\n ],\n ],\n};\n"],"mappings":";;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAAS,mBAAmB;;;ACA5B,SAAS,SAAS;AAEX,IAAM,iBAAiB,EAC3B,OAAO;AAAA,EACN,OAAO,EACJ,OAAO,EACP,WAAW,OAAO,EAClB;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,YAAY,EACT,OAAO,EACP,IAAI,EACJ;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,SAAS,EACN,OAAO,EACP;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,MAAM,EACH,OAAO,EACP;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,QAAQ,EACL,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,EAAE,QAAQ,CAAC,CAAC,EACvC;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,eAAe,EACZ,QAAQ,EACR;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,aAAa,EACV,QAAQ,EACR;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,aAAa,EACV,QAAQ,EACR,SAAS,yCAAyC,EAClD,SAAS;AAAA,EACZ,QAAQ,EACL,QAAQ,EACR,SAAS,+CAA+C,EACxD,SAAS;AAAA,EACZ,UAAU,EACP,OAAO,EACP;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,aAAa,EACV,KAAK,CAAC,WAAW,4BAA4B,MAAM,CAAC,EACpD,SAAS,uDAAuD,EAChE,SAAS;AACd,CAAC,EACA,OAAO,CAAC,MAAM,QAAQ,EAAE,KAAK,MAAM,QAAQ,EAAE,UAAU,GAAG;AAAA,EACzD,SAAS;AACX,CAAC;;;ACrEH,SAAS,KAAAA,UAAS;AAEX,IAAM,gBAAgBA,GAAE,OAAO;AAAA,EACpC,SAASA,GACN,OAAO,EACP;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,MAAMA,GACH,OAAO,EACP;AAAA,IACC;AAAA,EACF,EACC,SAAS;AAAA,EACZ,QAAQA,GACL,MAAMA,GAAE,OAAOA,GAAE,OAAO,GAAGA,GAAE,QAAQ,CAAC,CAAC,EACvC,SAAS,0CAA0C,EACnD,SAAS;AAAA,EACZ,UAAUA,GACP,OAAO,EACP,SAAS,+CAA+C,EACxD,SAAS;AAAA,EACZ,gBAAgBA,GACb,QAAQ,EACR,SAAS,wDAAwD,EACjE,SAAS;AAAA,EACZ,WAAWA,GACR,QAAQ,EACR,SAAS,+CAA+C,EACxD,SAAS;AAAA,EACZ,MAAMA,GACH,OAAO,EACP,SAAS,6CAA6C,EACtD,SAAS;AAAA,EACZ,IAAIA,GACD,QAAQ,EACR;AAAA,IACC;AAAA,EACF,EACC,SAAS;AACd,CAAC;;;AFjCM,IAAM,WAAW,YAAY,cAAc;AAC3C,IAAM,UAAU,YAAY,aAAa;;;AGThD;AAAA;AAAA;AAAA;AAAA;;;ACAA;AAAA;AAAA;AAAA;AAAA;AAEA,IAAM,oBAAoB;AAAA,EACxB,IAAI;AAAA,EACJ,SAAS;AAAA,EACT,IAAI;AACN;AAEA,IAAM,sBAAsB,EAAE,IAAI,KAAc;AAEhD,IAAM,iBAAiB;AAAA,EACrB,IAAI;AAAA,EACJ,SAAS,EAAE,IAAI,YAAY;AAC7B;AAEA,SAAS,mBAAoC;AAC3C,SAAO;AAAA,IACL,MAAM;AAAA,MACJ,aAAa,MAAM,QAAQ,QAAQ,iBAA0B;AAAA,MAC7D,eAAe,MAAM,QAAQ,QAAQ,mBAA4B;AAAA,IACnE;AAAA,IACA,eAAe;AAAA,MACb,MAAM,MAAM,QAAQ,QAAQ,cAAuB;AAAA,IACrD;AAAA,EACF;AACF;AAEO,IAAM,OAAY;AAAA,EACvB,aAAa,iBAAiB;AAAA,EAC9B,aAAa,MACX,QAAQ,QAAQ,EAAE,IAAI,KAAK,CAAU;AACzC;AAEO,IAAM,aAAa;AAAA,EACxB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;;;ACtCA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AACA,SAAS,gBAAgB;AAgClB,IAAM,gBAAkC;AAAA,EAC7C,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,kBAAkB;AAAA,IAC7B,WAAW;AAAA,IACX,MAAM;AAAA,MACJ,IAAI;AAAA,MACJ,OAAO;AAAA,MACP,UAAU;AAAA,MACV,SAAS;AAAA,IACX;AAAA,IACA,MAAM,EAAE,IAAI,WAAW;AAAA,EACzB,CAAC;AAAA,EACD,SAAS;AAAA,IACP,UAAU;AAAA,MACR,SAAS;AAAA,MACT,MAAM;AAAA,IACR;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH;AAAA,MACE;AAAA,MACA;AAAA,QACE,SAAS;AAAA,QACT,MAAM;AAAA,QACN,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AACF;AAKO,IAAM,aAA+B;AAAA,EAC1C,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,eAAe;AAAA,IAC1B,WAAW;AAAA,IACX,MAAM;AAAA,MACJ,SAAS;AAAA,MACT,MAAM;AAAA,MACN,UAAU;AAAA,IACZ;AAAA,EACF,CAAC;AAAA,EACD,SAAS;AAAA,IACP,UAAU;AAAA,MACR,SAAS;AAAA,MACT,MAAM;AAAA,IACR;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH;AAAA,MACE;AAAA,MACA;AAAA,QACE,SAAS;AAAA,QACT,MAAM;AAAA,QACN,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AACF;AAKO,IAAM,YAA8B;AAAA,EACzC,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,eAAe;AAAA,IAC1B,WAAW;AAAA,IACX,MAAM,EAAE,MAAM,aAAa;AAAA,IAC3B,MAAM,EAAE,IAAI,aAAa;AAAA,EAC3B,CAAC;AAAA,EACD,SAAS;AAAA,IACP,UAAU;AAAA,MACR,IAAI;AAAA,MACJ,MAAM;AAAA,MACN,MAAM;AAAA,IACR;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH,CAAC,kCAAkC,EAAE,OAAO,aAAa,CAAC;AAAA,IAC1D;AAAA,MACE;AAAA,MACA;AAAA,QACE,SAAS;AAAA,QACT,MAAM;AAAA,QACN,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AACF;AAKO,IAAM,uBAAyC;AAAA,EACpD,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,iBAAiB;AAAA,IAC5B,WAAW;AAAA,IACX,MAAM,EAAE,MAAM,WAAW,WAAW,oBAAoB;AAAA,EAC1D,CAAC;AAAA,EACD,SAAS;AAAA,IACP,UAAU;AAAA,MACR,SAAS;AAAA,MACT,MAAM;AAAA,MACN,UAAU;AAAA,MACV,gBAAgB;AAAA,IAClB;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH;AAAA,MACE;AAAA,MACA;AAAA,QACE,SAAS;AAAA,QACT,MAAM;AAAA,QACN,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,QACR,WAAW;AAAA,QACX,iBAAiB;AAAA,MACnB;AAAA,IACF;AAAA,EACF;AACF;AAKO,IAAM,mBAAqC;AAAA,EAChD,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,iBAAiB;AAAA,IAC5B,WAAW;AAAA,IACX,MAAM,EAAE,WAAW,EAAE;AAAA,EACvB,CAAC;AAAA,EACD,SAAS;AAAA,IACP,UAAU;AAAA,MACR,SAAS;AAAA,MACT,WAAW;AAAA,MACX,MAAM;AAAA,MACN,MAAM;AAAA,IACR;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH;AAAA,MACE;AAAA,MACA;AAAA,QACE,SAAS;AAAA,QACT,MAAM;AAAA,QACN,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,QACR,MAAM;AAAA,MACR;AAAA,IACF;AAAA,EACF;AACF;AAMO,IAAM,gBAAkC;AAAA,EAC7C,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,eAAe;AAAA,IAC1B,WAAW;AAAA,IACX,MAAM,EAAE,MAAM,QAAQ,OAAO,kBAAkB;AAAA,IAC/C,QAAQ,EAAE,MAAM,UAAU,IAAI,OAAO,aAAa,GAAG;AAAA,EACvD,CAAC;AAAA,EACD,SAAS;AAAA,IACP,UAAU;AAAA,MACR,SAAS;AAAA,IACX;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH;AAAA,MACE;AAAA,MACA;AAAA,QACE,SAAS;AAAA,QACT,MAAM;AAAA,QACN,QAAQ;AAAA,UACN;AAAA,YACE,MAAM;AAAA,YACN,MAAM,EAAE,MAAM,cAAc,MAAM,cAAc;AAAA,UAClD;AAAA,UACA;AAAA,YACE,MAAM;AAAA,YACN,QAAQ;AAAA,cACN,EAAE,MAAM,UAAU,MAAM,gBAAgB;AAAA,cACxC,EAAE,MAAM,UAAU,MAAM,4BAA4B;AAAA,YACtD;AAAA,UACF;AAAA,UACA;AAAA,YACE,MAAM;AAAA,YACN,UAAU,CAAC,EAAE,MAAM,UAAU,MAAM,cAAc,CAAC;AAAA,UACpD;AAAA,QACF;AAAA,QACA,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AACF;AAOO,IAAM,qBAAuC;AAAA,EAClD,OAAO;AAAA,EACP,aACE;AAAA,EACF,IAAI,SAAS,mBAAmB;AAAA,IAC9B,WAAW;AAAA,IACX,MAAM,EAAE,SAAS,SAAS,aAAa,OAAO;AAAA,EAChD,CAAC;AAAA,EACD,UAAU;AAAA,IACR,OAAO;AAAA,IACP,YAAY;AAAA,EACd;AAAA,EACA,SAAS;AAAA,IACP,UAAU;AAAA,MACR,MAAM;AAAA,IACR;AAAA,EACF;AAAA,EACA,KAAK;AAAA,IACH;AAAA,MACE;AAAA,MACA;AAAA,MACA,KAAK,UAAU;AAAA,QACb,MAAM;AAAA,QACN,cAAc;AAAA,QACd,cAAc;AAAA,QACd,QAAQ;AAAA,MACV,CAAC;AAAA,IACH;AAAA,EACF;AACF;","names":["z"]}
@@ -76,6 +76,8 @@ __export(step_exports, {
76
76
  });
77
77
  var import_core = require("@walkeros/core");
78
78
  var purchaseAlert = {
79
+ title: "Purchase alert",
80
+ description: "A completed order posts a templated message to a sales channel via the Slack Web API.",
79
81
  in: (0, import_core.getEvent)("order complete", {
80
82
  timestamp: 1700000100,
81
83
  data: {
@@ -106,6 +108,8 @@ var purchaseAlert = {
106
108
  ]
107
109
  };
108
110
  var errorAlert = {
111
+ title: "Error alert",
112
+ description: "An error event posts a critical alert to an engineering channel using a mapping-level channel override.",
109
113
  in: (0, import_core.getEvent)("error occur", {
110
114
  timestamp: 1700000200,
111
115
  data: {
@@ -134,6 +138,8 @@ var errorAlert = {
134
138
  ]
135
139
  };
136
140
  var welcomeDM = {
141
+ title: "Welcome DM",
142
+ description: "A user signup opens a Slack DM channel and posts a welcome message with the selected plan.",
137
143
  in: (0, import_core.getEvent)("user signup", {
138
144
  timestamp: 1700000300,
139
145
  data: { plan: "enterprise" },
@@ -161,6 +167,8 @@ var welcomeDM = {
161
167
  ]
162
168
  };
163
169
  var threadedCheckoutStep = {
170
+ title: "Threaded reply",
171
+ description: "A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.",
164
172
  in: (0, import_core.getEvent)("checkout step", {
165
173
  timestamp: 1700000400,
166
174
  data: { step: "payment", sessionTs: "1700000000.000050" }
@@ -189,6 +197,8 @@ var threadedCheckoutStep = {
189
197
  ]
190
198
  };
191
199
  var ephemeralMessage = {
200
+ title: "Ephemeral message",
201
+ description: "A quota warning posts an ephemeral Slack message visible only to a target admin user.",
192
202
  in: (0, import_core.getEvent)("quota warning", {
193
203
  timestamp: 1700000500,
194
204
  data: { remaining: 5 }
@@ -216,6 +226,8 @@ var ephemeralMessage = {
216
226
  ]
217
227
  };
218
228
  var defaultBlocks = {
229
+ title: "Default blocks",
230
+ description: "With no custom text the destination auto-generates a Block Kit message from event data and source.",
219
231
  in: (0, import_core.getEvent)("lead submit", {
220
232
  timestamp: 1700000600,
221
233
  data: { name: "Acme", email: "sales@acme.test" },
@@ -257,6 +269,8 @@ var defaultBlocks = {
257
269
  ]
258
270
  };
259
271
  var deployNotification = {
272
+ title: "Webhook deploy",
273
+ description: "Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.",
260
274
  in: (0, import_core.getEvent)("deploy complete", {
261
275
  timestamp: 1700000700,
262
276
  data: { version: "1.4.2", environment: "prod" }
@@ -55,6 +55,8 @@ __export(step_exports, {
55
55
  });
56
56
  import { getEvent } from "@walkeros/core";
57
57
  var purchaseAlert = {
58
+ title: "Purchase alert",
59
+ description: "A completed order posts a templated message to a sales channel via the Slack Web API.",
58
60
  in: getEvent("order complete", {
59
61
  timestamp: 1700000100,
60
62
  data: {
@@ -85,6 +87,8 @@ var purchaseAlert = {
85
87
  ]
86
88
  };
87
89
  var errorAlert = {
90
+ title: "Error alert",
91
+ description: "An error event posts a critical alert to an engineering channel using a mapping-level channel override.",
88
92
  in: getEvent("error occur", {
89
93
  timestamp: 1700000200,
90
94
  data: {
@@ -113,6 +117,8 @@ var errorAlert = {
113
117
  ]
114
118
  };
115
119
  var welcomeDM = {
120
+ title: "Welcome DM",
121
+ description: "A user signup opens a Slack DM channel and posts a welcome message with the selected plan.",
116
122
  in: getEvent("user signup", {
117
123
  timestamp: 1700000300,
118
124
  data: { plan: "enterprise" },
@@ -140,6 +146,8 @@ var welcomeDM = {
140
146
  ]
141
147
  };
142
148
  var threadedCheckoutStep = {
149
+ title: "Threaded reply",
150
+ description: "A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.",
143
151
  in: getEvent("checkout step", {
144
152
  timestamp: 1700000400,
145
153
  data: { step: "payment", sessionTs: "1700000000.000050" }
@@ -168,6 +176,8 @@ var threadedCheckoutStep = {
168
176
  ]
169
177
  };
170
178
  var ephemeralMessage = {
179
+ title: "Ephemeral message",
180
+ description: "A quota warning posts an ephemeral Slack message visible only to a target admin user.",
171
181
  in: getEvent("quota warning", {
172
182
  timestamp: 1700000500,
173
183
  data: { remaining: 5 }
@@ -195,6 +205,8 @@ var ephemeralMessage = {
195
205
  ]
196
206
  };
197
207
  var defaultBlocks = {
208
+ title: "Default blocks",
209
+ description: "With no custom text the destination auto-generates a Block Kit message from event data and source.",
198
210
  in: getEvent("lead submit", {
199
211
  timestamp: 1700000600,
200
212
  data: { name: "Acme", email: "sales@acme.test" },
@@ -236,6 +248,8 @@ var defaultBlocks = {
236
248
  ]
237
249
  };
238
250
  var deployNotification = {
251
+ title: "Webhook deploy",
252
+ description: "Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.",
239
253
  in: getEvent("deploy complete", {
240
254
  timestamp: 1700000700,
241
255
  data: { version: "1.4.2", environment: "prod" }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "$meta": {
3
3
  "package": "@walkeros/server-destination-slack",
4
- "version": "3.4.0",
4
+ "version": "3.4.1-next-1776790594143",
5
5
  "type": "destination",
6
6
  "platform": [
7
7
  "server"
@@ -153,6 +153,8 @@
153
153
  },
154
154
  "step": {
155
155
  "defaultBlocks": {
156
+ "title": "Default blocks",
157
+ "description": "With no custom text the destination auto-generates a Block Kit message from event data and source.",
156
158
  "in": {
157
159
  "name": "lead submit",
158
160
  "data": {
@@ -203,7 +205,7 @@
203
205
  "group": "gr0up",
204
206
  "count": 1,
205
207
  "version": {
206
- "source": "3.4.0",
208
+ "source": "3.4.1-next-1776790594143",
207
209
  "tagging": 1
208
210
  },
209
211
  "source": {
@@ -262,6 +264,8 @@
262
264
  ]
263
265
  },
264
266
  "deployNotification": {
267
+ "title": "Webhook deploy",
268
+ "description": "Without a token the destination posts to an incoming Slack webhook URL with the rendered message body.",
265
269
  "in": {
266
270
  "name": "deploy complete",
267
271
  "data": {
@@ -312,7 +316,7 @@
312
316
  "group": "gr0up",
313
317
  "count": 1,
314
318
  "version": {
315
- "source": "3.4.0",
319
+ "source": "3.4.1-next-1776790594143",
316
320
  "tagging": 1
317
321
  },
318
322
  "source": {
@@ -338,6 +342,8 @@
338
342
  ]
339
343
  },
340
344
  "ephemeralMessage": {
345
+ "title": "Ephemeral message",
346
+ "description": "A quota warning posts an ephemeral Slack message visible only to a target admin user.",
341
347
  "in": {
342
348
  "name": "quota warning",
343
349
  "data": {
@@ -387,7 +393,7 @@
387
393
  "group": "gr0up",
388
394
  "count": 1,
389
395
  "version": {
390
- "source": "3.4.0",
396
+ "source": "3.4.1-next-1776790594143",
391
397
  "tagging": 1
392
398
  },
393
399
  "source": {
@@ -419,6 +425,8 @@
419
425
  ]
420
426
  },
421
427
  "errorAlert": {
428
+ "title": "Error alert",
429
+ "description": "An error event posts a critical alert to an engineering channel using a mapping-level channel override.",
422
430
  "in": {
423
431
  "name": "error occur",
424
432
  "data": {
@@ -470,7 +478,7 @@
470
478
  "group": "gr0up",
471
479
  "count": 1,
472
480
  "version": {
473
- "source": "3.4.0",
481
+ "source": "3.4.1-next-1776790594143",
474
482
  "tagging": 1
475
483
  },
476
484
  "source": {
@@ -499,6 +507,8 @@
499
507
  ]
500
508
  },
501
509
  "purchaseAlert": {
510
+ "title": "Purchase alert",
511
+ "description": "A completed order posts a templated message to a sales channel via the Slack Web API.",
502
512
  "in": {
503
513
  "name": "order complete",
504
514
  "data": {
@@ -582,7 +592,7 @@
582
592
  "group": "gr0up",
583
593
  "count": 1,
584
594
  "version": {
585
- "source": "3.4.0",
595
+ "source": "3.4.1-next-1776790594143",
586
596
  "tagging": 1
587
597
  },
588
598
  "source": {
@@ -611,6 +621,8 @@
611
621
  ]
612
622
  },
613
623
  "threadedCheckoutStep": {
624
+ "title": "Threaded reply",
625
+ "description": "A checkout step posts as a threaded reply in Slack via thread_ts with broadcast to the channel.",
614
626
  "in": {
615
627
  "name": "checkout step",
616
628
  "data": {
@@ -661,7 +673,7 @@
661
673
  "group": "gr0up",
662
674
  "count": 1,
663
675
  "version": {
664
- "source": "3.4.0",
676
+ "source": "3.4.1-next-1776790594143",
665
677
  "tagging": 1
666
678
  },
667
679
  "source": {
@@ -694,6 +706,8 @@
694
706
  ]
695
707
  },
696
708
  "welcomeDM": {
709
+ "title": "Welcome DM",
710
+ "description": "A user signup opens a Slack DM channel and posts a welcome message with the selected plan.",
697
711
  "in": {
698
712
  "name": "user signup",
699
713
  "data": {
@@ -741,7 +755,7 @@
741
755
  "group": "gr0up",
742
756
  "count": 1,
743
757
  "version": {
744
- "source": "3.4.0",
758
+ "source": "3.4.1-next-1776790594143",
745
759
  "tagging": 1
746
760
  },
747
761
  "source": {
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@walkeros/server-destination-slack",
3
3
  "description": "Slack server destination for walkerOS (Incoming Webhook + @slack/web-api, Block Kit, channel routing, threading, DMs)",
4
- "version": "3.4.0",
4
+ "version": "3.4.1-next-1776790594143",
5
5
  "license": "MIT",
6
6
  "exports": {
7
7
  ".": {
@@ -35,11 +35,11 @@
35
35
  },
36
36
  "dependencies": {
37
37
  "@slack/web-api": "^7.0.0",
38
- "@walkeros/core": "3.4.0",
39
- "@walkeros/server-core": "3.4.0"
38
+ "@walkeros/core": "3.4.1-next-1776790594143",
39
+ "@walkeros/server-core": "3.4.1-next-1776790594143"
40
40
  },
41
41
  "devDependencies": {
42
- "@walkeros/collector": "3.4.0"
42
+ "@walkeros/collector": "3.4.1-next-1776790594143"
43
43
  },
44
44
  "repository": {
45
45
  "url": "git+https://github.com/elbwalker/walkerOS.git",