Guide

Lead Gen (Advanced DM Flow) - Mobile Integration Guide

Lead Gen is a multi-step DM automation builder that allows users to create flows triggered by comments on posts or replies to stories. It supports lead collection (email, phone, name), delays, tags, b

Meta Business Partner
30,000+ creators
$9.99/mo flat

Overview

Lead Gen is a multi-step DM automation builder that allows users to create flows triggered by comments on posts or replies to stories. It supports lead collection (email, phone, name), delays, tags, button templates, and a followers-only gate. It works for:

  • Single post automation - triggered by comments on a specific post
  • Single story automation - triggered by replies to a specific story
  • Global post automation - triggered by comments on ALL posts
  • Global story automation - triggered by replies to ALL stories

1. Entry Points

1.1 Manage Post Page (Single Post/Story)

When a user opens a specific post or story to manage, the "Lead Gen" card appears alongside "Send Link or Images".

  • Card title: "Lead Gen"
  • Card description: "Build a multi-step DM automation with lead collection (email, phone, name), delays, tags, and button templates - all triggered by comments on this post."
  • Toggle (Switch): Shows enabled/disabled based on whether flow_ids from the automate-post API response contains a key starting with comment-flow-
  • Click action: Opens the Lead Gen flow editor (LinearFlowView)

Visibility rules:

  • Shown for posts, stories, and global automations
  • Hidden for collab posts where user doesn't have view permission
  • Hidden when igDetail has an error (unless it's a scheduled post, FB, or global)

1.2 Global Automation Page

On the global automation list page, Lead Gen entries appear alongside regular trigger word automations.

  • Display: Purple "Lead Gen" tag + trigger word tags + "Edit" button
  • Data source: Extracted from quick_gloabl_flow.triger_words in the quick-global-automate-posts API response
  • Edit URL: /manage-post/{postId}?post_type={posts|stories}&platform_type={insta|fb}&is_global=true&lead_gen=true

2. API Endpoints

2.1 Get Post Automation Config

GET /automate-post?post_id={postId}

Response includes:

{
  "data": { ... },
  "ig_post_data": { ... },
  "flow_ids": {
    "comment-flow-{postId}": {
      "automate_all": "false",
      "trigger_words": ["keyword1", "keyword2"]
    }
  },
  "code": 200
}
  • If flow_ids contains a key starting with comment-flow-, Lead Gen is enabled for this post
  • NOT called when URL has lead_gen=true (global lead gen edit)

2.2 Get Global Automation Config

GET /quick-global-automate-posts
GET /quick-global-automate-posts?is_story=true

Response includes:

{
  "data": {
    "triger_words": {
      "*allwordautomation*": "uuid-id",
      "keyword": "uuid-id"
    }
  },
  "quick_gloabl_flow": {
    "type": "comment_reply",
    "triger_words": {
      "trigger-word-name": ["comment-flow-{globalId}"]
    }
  },
  "code": 200
}
  • Entries in quick_gloabl_flow.triger_words where the flow ID array contains a comment-flow- prefixed ID are Lead Gen automations

2.3 Save Draft (Firebase)

Firestore: automations/{userId}/draft_automations/{flowId}
  • flowId format: comment-flow-{postId}
  • Stores the full flow payload + cleanAutomationData (the LinearFlowView format)
  • live: true/false indicates publish status

2.4 Publish Flow

POST /flow_editor?flow_id=comment-flow-{postId}

Request body:

{
  "name": "Flow Name",
  "live": true,
  "comment_automation": true,
  "quick_dm": true,
  "cleanAutomationData": { ... },
  "nodes": [ ... ],
  "edges": [ ... ]
}

2.5 Get Published Flow (for discard)

GET /flow_editor?flow_id=comment-flow-{postId}

2.6 Delete/Unpublish Flow

DELETE /flow_editor?flow_id=comment-flow-{postId}

2.7 Get Lead Gen Contacts

GET /flow_editor_response?flow_id=comment-flow-{postId}

Response:

{
  "data": [
    {
      "created_at": "2026-04-05 17:13:14.206741",
      "flow_completed": true,
      "flow_id": "comment-flow-{postId}",
      "message_count": "4",
      "parent_id": "recipientId-senderId-flowId",
      "question_response": [
        {
          "question": "email please",
          "user_response": "user@example.com",
          "skip": false,
          "id": "q-1",
          "sender_id": "4160762890722152",
          "updated_at": "2026-04-05 17:13:34.472381"
        }
      ],
      "sender_detail": {
        "id": "4160762890722152",
        "username": "user_handle"
      },
      "sender_id": "4160762890722152",
      "tags": [
        { "name": "tag-name", "id": "tagDocId" }
      ],
      "contact_info": {
        "flow_end": true,
        "human_takeover": false,
        "processing_by_ai": false
      }
    }
  ]
}

2.8 Save to Library (Firebase)

Firestore: saved_leadgen_automations/{autoDocId}

Document:

{
  "user_id": "userId",
  "name": "Flow Name",
  "config": { ... },
  "type": "lead_gen",
  "flow_id": "comment-flow-{postId}",
  "createdAt": serverTimestamp
}

3. Data Model - LinearFlowView Format (cleanAutomationData)

This is the simplified format stored in cleanAutomationData and used by the LinearFlowView editor.

{
  "id": "comment-flow-{postId}",
  "name": "Flow Name",
  "live": false,
  "isGlobal": false,
  "trigger": {
    "type": "comment_reply | story_reply",
    "keywords": ["link", "info"],
    "automate_all": false,
    "match_exact_word": false,
    "selected_posts": ["postId1"],
    "all_posts": "true | false",
    "all_stories": "true | false",
    "comment_response": ["Thanks! Check DM", "Sent ✅"]
  },
  "welcome_message": {
    "title": "Thanks for commenting! Click below to get your content.",
    "description": "",
    "button": "Send me the link"
  },
  "steps": [ ... ],
  "confirmation": { "text": "" }
}

3.1 Trigger Types

Comment Reply (comment_reply):

  • keywords: array of trigger words
  • automate_all: boolean - automate all comments
  • match_exact_word: boolean
  • selected_posts: array of post IDs (empty for global)
  • all_posts: "true" for global, "false" for specific post
  • comment_response: array of reply comment texts (one random reply per comment)

Story Reply (story_reply):

  • keywords: array of trigger words
  • automate_all: boolean - automate all replies
  • match_exact_word: boolean
  • selected_posts: array of story IDs (empty for global)
  • all_stories: "true" for global, "false" for specific story
  • No comment_response (stories don't have comments)

3.2 Welcome Message (Comment mode only, NOT for stories)

{
  "title": "Thanks for commenting! Click below to get your content.",
  "description": "",
  "button": "Send me the link"
}
  • Rendered as a button template card in DM
  • User taps the button → proceeds to next step
  • Default title: "Thanks for commenting! Click below to get your content."
  • Default button: "Send me the link"

4. Step Types

4.1 Message (type: "message")

{
  "id": "step-123",
  "type": "message",
  "messageType": "text | button | image",
  "text": "Here is your link: https://example.com",
  "image_url": "https://...",
  "templates": [
    {
      "id": "tpl-123",
      "title": "Card Title",
      "description": "Card description",
      "thumb_url": "https://...",
      "buttons": [
        { "title": "Visit", "url": "https://...", "type": "web_url" }
      ]
    }
  ]
}
  • Text: plain text message, supports link preview (first URL extracted via regex, preview fetched from https://curly-surf-0de5.sanjayhotaction.workers.dev/?url={encodedUrl})
  • Button: card template with title, description, image, up to 3 buttons with URLs
  • Image: image message with image_url

4.2 Question (type: "question")

{
  "id": "step-123",
  "type": "question",
  "questionType": "email | phone | name | custom_input",
  "question": "What's your email?",
  "skip_option": { "enable": false },
  "retry_attempt": { "count": 3 },
  "wrong_input": { "message": "" },
  "variable": ""
}
  • Bot sends the question, waits for user response
  • questionType determines validation: email validates email format, phone validates phone, name accepts any text, custom_input accepts any text
  • skip_option.enable: if true, user can skip this question
  • retry_attempt.count: number of retries on invalid input

4.3 Delay (type: "delay")

{
  "id": "step-123",
  "type": "delay",
  "duration": 3,
  "durationType": "s | m | h"
}
  • Pauses the flow for the specified duration
  • s = seconds, m = minutes, h = hours

4.4 Tag Contact (type: "tag")

{
  "id": "step-123",
  "type": "tag",
  "tags": ["tagId1", "tagId2"],
  "tagsData": [
    { "label": "VIP", "value": "tagId1", "name": "VIP" }
  ]
}
  • Tags the contact with specified tags
  • Tags are fetched from Firestore: users/{userId}/tags

4.5 Followers Only Gate (type: "followers_only")

{
  "id": "step-123",
  "type": "followers_only",
  "message_reply": "true | false",
  "message": {
    "title": "Follow for exclusive content",
    "description": "",
    "open_profile_text": "Open Profile",
    "button": "I started following you"
  },
  "follow_up_duration": 30,
  "follow_up_duration_type": "m"
}

Behavior:

  • Checks if the user follows the account
  • If following: proceeds to next step via {nodeId}-follow-flow connection
  • If NOT following and message_reply = "true": sends a button template with:
    • Title + description
    • "Open Profile" button - opens the account profile
    • "I started following you" button - re-checks if user followed
  • If NOT following and message_reply = "false": routes to a separate flow (not used in LinearFlowView)
  • Follow-up: if enabled (follow_up_duration > 0), after the specified time, moves to next step via {nodeId}-followup connection even if user didn't follow

Edge connections (important for payload):

  • {nodeId}-follow-flow-right → connects to next step (user IS following)
  • {nodeId}-followup-right → connects to next step (follow-up timer expired, only if follow_up_duration > 0)
  • Regular edges use {nodeId}-right as sourceHandle

5. Flow Editor Payload (nodes/edges format)

The LinearFlowView format is converted to the flow editor payload for the backend. This is the nodes and edges format.

5.1 Node Types

LinearFlowView type Node type Notes
trigger triggerComp Always node-1, contains auto_reply config
message messageReply Contains messages array
question questionNode Contains messages array with question config
delay messageReply Message with type: "delay"
tag tagContact Contains tags and tagsData
followers_only followersOnly Contains followers_only, message, follow_up_duration

5.2 Trigger Node Data Structure

{
  "id": "node-1",
  "type": "triggerComp",
  "data": {
    "auto_reply": {
      "dm_reply": {
        "enabled": false,
        "automate_all": "false",
        "triger_words": []
      },
      "story_reply": {
        "enabled": true,
        "automate_all": "true | false",
        "triger_words": ["keyword"],
        "all_stories": "true | false",
        "selected_posts": [],
        "match_exact_word": false
      },
      "comment_reply": {
        "enabled": true,
        "automate_all": "true | false",
        "triger_words": ["keyword"],
        "all_posts": "true | false",
        "selected_posts": ["postId"],
        "comment_response": ["reply text"],
        "match_exact_word": false
      },
      "welcome_message": {
        "title": "...",
        "description": "",
        "button": "Send me the link"
      }
    }
  }
}
  • Only ONE of story_reply.enabled or comment_reply.enabled is true
  • dm_reply is always disabled for Lead Gen

5.3 Edge Structure

{
  "id": "e-node-1-step-1",
  "source": "node-1",
  "target": "step-1",
  "sourceHandle": "node-1-right",
  "targetHandle": "step-1-left",
  "type": "custom-edge",
  "markerEnd": { "type": "arrowclosed" },
  "data": {}
}

Special edge handles for followers_only:

  • Source from followers_only to next step: sourceHandle: "{nodeId}-follow-flow-right"
  • Follow-up edge (only if follow_up_duration > 0): sourceHandle: "{nodeId}-followup-right"

6. UI Screens & Components

6.1 Trigger Configuration (Entry Point card)

For Comment mode (posts):

  1. Post preview (image, caption, likes, comments) - or "🌐 All Posts - Global Automation" banner for global
  2. Step 1: Trigger Keywords - Custom Keywords / All Comments toggle, keyword input, match exact word checkbox
  3. Step 2: Reply to Comment (optional) - comment reply input, displayed as tags
  4. Step 3: Welcome Message - button template card editor (title + button text, no description, no image)

For Story mode:

  1. Story preview (image, caption, username) - or "🌐 All Stories - Global Automation" banner for global
  2. Step 1: Trigger Keywords - Custom Keywords / All Replies toggle, keyword input, match exact word checkbox
  3. No welcome message
  4. No reply to comment

6.2 Step Editor Cards

Each step is rendered as a card in the flow timeline with:

  • Step type icon and label (e.g., "MESSAGE", "QUESTION", "FOLLOWERS ONLY")
  • Inline editing (click to edit text, buttons, etc.)
  • Move up/down buttons
  • Delete button
  • "Add Step" button between steps

6.3 Chat Preview (Phone Mockup)

Comment mode - two tabs:

  • 💬 Comment tab: Instagram post image full-screen with bottom sheet overlay showing trigger comments and reply comments
  • ✉️ DMs tab: DM conversation preview with context line "You replied to lead for commenting on your post", welcome message card, and all steps

Story mode - no tabs, DM view only:

  • Context line: "Lead replied to your story"
  • Story thumbnail image + trigger keyword with typing animation (stacked vertically)
  • Steps rendered below

Tab switching:

  • Editing trigger keywords or reply comments → switches to Comment tab
  • Editing welcome message or steps → switches to DMs tab
  • Story mode always shows DM view

6.4 Followers Only Gate Card

Displays:

  1. "Followers Only Gate" header with icon
  2. "If not following:" label
  3. Button template card with:
    • Title (editable)
    • Description (editable)
    • "Open Profile" button (editable text)
    • "I started following you" button (editable text)
  4. "🔄 'I started following you' → re-checks if user followed" info line
  5. "Move to next step if not followed" toggle with time delay (number + sec/min/hour)
  6. "✅ Move to next step" indicator inside the follow-up section

6.5 Lead Gen Contacts Table

Displayed in the manage post page's second tab (replaces "All Comments" when Lead Gen is enabled).

Table columns:

  • Contact: avatar, name, @username, Instagram icon link (https://instagram.com/{username})
  • Tags: colored tag pills
  • Date: created_at formatted to local time
  • Status: "Completed" (green) or "In Progress" (orange)

Expandable rows: question responses with question text and user's answer (or "Skipped" tag)

CSV Download: exports Username, Name, Instagram URL, all question responses as dynamic columns, Tags, Status, Date


7. Link Preview

For text messages containing URLs, a link preview is shown.

Extraction: First https:// or http:// URL extracted via regex from message text.

Preview API:

GET https://curly-surf-0de5.sanjayhotaction.workers.dev/?url={encodedUrl}

Response:

{
  "title": "Page Title",
  "description": "Page description",
  "image": "https://og-image-url.jpg"
}

Display: Card with image, title, description, domain - rendered ABOVE the text message.


8. Publish Flow

8.1 Save to Draft

  • Saves to Firebase: automations/{userId}/draft_automations/comment-flow-{postId}
  • Includes both the flow editor payload (nodes/edges) and cleanAutomationData (LinearFlowView format)

8.2 Publish & Activate

  1. Save draft first
  2. POST to /flow_editor?flow_id=comment-flow-{postId} with live: true
  3. Update Firebase draft with live: true
  4. Save to library: saved_leadgen_automations collection
  5. Show success message, reload page after 1.5s

8.3 Discard Draft

  1. GET /flow_editor?flow_id=comment-flow-{postId} to fetch live version
  2. Overwrite Firebase draft with live version
  3. Reload the editor

9. Flow ID Convention

Context Flow ID format Example
Single post comment-flow-{igPostId} comment-flow-18131564404539322
Single story comment-flow-{igStoryId} comment-flow-18131564404539322
Global post comment-flow-{globalUUID} comment-flow-2336b1c4-61a7-4d27-b2f3-78caa76da97b
Global story comment-flow-{globalUUID} comment-flow-2336b1c4-61a7-4d27-b2f3-78caa76da97b

10. URL Parameters

Parameter Values Description
post_type posts, stories, live, next-post Type of content being automated
platform_type insta, fb Platform
is_global true Global automation (all posts/stories)
lead_gen true Lead Gen edit mode - skips automate-post API call, sets default empty data
flow_editor true/false Legacy flow editor flag

11. Detection Logic

Is Lead Gen enabled for a post?

const hasLeadGen = Object.keys(flowIds).some(k => k.startsWith('comment-flow-'));

Is it a Lead Gen entry in global automation list?

const commentFlowId = (flowIds || []).find(fid => fid.startsWith('comment-flow-'));

Should we show Lead Gen contacts instead of regular comments?

const showLeadGenContacts = Object.keys(flowIds).some(k => k.startsWith('comment-flow-'));

12. Known Issues / Missing Items

  1. No global_automation flag in publish payload - convertToFlowPayload doesn't include global_automation: true for global automations. The regular publish adds this. Backend may need it.

  2. Lead Gen disable doesn't unpublish the flow - The Switch toggle on the Lead Gen card calls showConfirm('Auto Reply') which disables the regular automation. It should call DELETE /flow_editor?flow_id=comment-flow-{postId} to unpublish the lead gen flow.

  3. Library saves duplicate on every publish - addDoc creates a new document each time. Should use setDoc with the flow ID as document ID, or check for existing entry first.

  4. one_time_only not exposed - The flow editor trigger has a one_time_only option (reply once per day vs first time only). Not exposed in the Lead Gen editor UI.

  5. post_type not in flow payload - The regular publish adds post_type: "story" for stories. The Lead Gen publish doesn't include this.

  6. No Shopify product step - The flow editor supports Shopify product nodes but the LinearFlowView doesn't have this step type.

  7. AI Reply node - The flow editor has an AI Reply node. Not available in LinearFlowView.

Ready to Automate Your Instagram DMs?

Join 30,000+ creators and brands using InstantDM today.

Start Your Free Trial

No credit card required. Setup in under 15 minutes.