> ## Documentation Index
> Fetch the complete documentation index at: https://docs.hiveku.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Workflow Recipe: Lead Scoring Based on Behavior

> Automatically score leads so your sales team focuses on the hottest prospects

Not every lead is worth a sales call. This recipe scores your leads based on their behavior and firmographics, so your team spends time on the ones most likely to close.

<Info>
  Before you start: you need CRM contacts with email tracking, page visit tracking, and form submission data. If activity isn't being logged, there's nothing to score.
</Info>

## Two Approaches

<CardGroup cols={2}>
  <Card title="Rule-based" icon="list-check">
    Hand-tuned point system. Transparent and adjustable.
  </Card>

  <Card title="AI-based" icon="wand-magic-sparkles">
    Let the AI score based on context. Less tuning, less transparency.
  </Card>
</CardGroup>

## Option 1: Rule-Based Scoring

<Tabs>
  <Tab title="Point System">
    Start with a simple additive model:

    | Signal                       | Points |
    | ---------------------------- | ------ |
    | Visited pricing page         | +20    |
    | Opened last 3 emails         | +15    |
    | Submitted a form             | +25    |
    | Company size > 50 employees  | +10    |
    | Role is Director or above    | +15    |
    | Responded to last cold email | +30    |
    | Unsubscribed                 | -50    |
    | No engagement in 30+ days    | -20    |

    A score of 0-40 is cold, 41-74 is warm, 75+ is hot.
  </Tab>

  <Tab title="Workflow">
    ```
    Trigger: Schedule (hourly)
    ├── Query: all leads updated in the last hour
    └── For each lead:
        ├── Compute: score = sum of applicable rules
        ├── Update: lead.score = computed
        └── If score >= 75:
            ├── Move to 'Hot' pipeline stage
            └── Notify sales via Slack
    ```
  </Tab>
</Tabs>

## Step 1: Create the Workflow

<Steps>
  <Step title="Open Workflows">
    Go to **Workflows > New Workflow**. Name it `Lead Scoring`.
  </Step>

  <Step title="Add a Schedule trigger">
    Set to **every hour** for near-real-time scoring, or **daily** if you don't need fast turnaround.
  </Step>

  <Step title="Query leads to score">
    ```sql theme={null}
    SELECT l.id, l.email, l.company, l.title, l.company_size,
           l.last_email_opened_at, l.last_page_visit_url, l.updated_at
    FROM leads l
    WHERE l.updated_at > now() - interval '1 hour'
       OR l.score IS NULL
    ```

    This catches new leads and any with recent activity.
  </Step>
</Steps>

## Step 2: Compute the Score

Add a **Code** action (JavaScript) or a series of **Condition** steps. The code action is usually cleaner:

```javascript theme={null}
let score = 0;

// Behavior
if (lead.visited_pricing_page) score += 20;
if (lead.emails_opened_recently >= 3) score += 15;
if (lead.form_submitted) score += 25;
if (lead.responded_to_cold_email) score += 30;

// Firmographics
if (lead.company_size > 50) score += 10;
if (['Director', 'VP', 'CEO', 'CTO'].some(t => lead.title?.includes(t))) score += 15;

// Penalties
if (lead.unsubscribed) score -= 50;
if (lead.days_since_activity > 30) score -= 20;

return Math.max(0, score);
```

Update the lead:

```sql theme={null}
UPDATE leads SET score = {{computed_score}}, scored_at = now() WHERE id = '{{item.id}}'
```

## Step 3: Route Hot Leads

<Steps>
  <Step title="Add a Condition step">
    ```
    {{computed_score}} >= 75
    ```
  </Step>

  <Step title="Move to Hot pipeline stage">
    Database update or CRM API call to change the lead's stage.
  </Step>

  <Step title="Notify sales">
    Add a Slack message action. Send to `#sales-hot-leads` with the lead's name, company, score, and why they're hot (top 3 signals).

    <Tip>
      Don't dump raw data — format the message so a rep can scan it in 2 seconds. Include a one-click link to open the lead in your CRM.
    </Tip>
  </Step>
</Steps>

## Option 2: AI-Based Scoring

If you don't want to hand-tune rules, let the AI do it.

Add an **AI Action** in the workflow:

```
Score this lead on a 1-100 scale based on likelihood to convert.

Company: {{item.company}}
Role: {{item.title}}
Company size: {{item.company_size}}
Recent activity: {{item.recent_activity}}
Last 5 pages visited: {{item.page_visits}}
Emails opened: {{item.emails_opened_count}} of {{item.emails_sent_count}}

Return only the number, no explanation.
```

Parse the response and save as `lead.score`.

AI scoring works well when you have rich context per lead. It's weaker when you need to explain *why* a score is what it is — reps sometimes want that transparency.

## Displaying Scores in the CRM

Show scores in your CRM contact list with color coding:

* **75+ (Hot)** — red/green badge, pinned at top
* **41-74 (Warm)** — yellow badge
* **0-40 (Cold)** — gray

Add a "Hot Leads" filter preset to the CRM so reps can jump to them instantly.

## Using Scores in Sequences

Route different messaging based on score:

* **Hot:** immediate personal outreach from a rep, demo CTA
* **Warm:** educational content, case studies
* **Cold:** nurture sequence, drip campaign

See [Cold Email](/how-tos/cold-email) for sequence setup.

<Tip>
  Review your scoring model monthly. Pull a list of leads that actually closed and see what their scores were 30 days earlier. If the scores don't predict closed deals, the weights are off — adjust until they do.
</Tip>

## Verify It Worked

1. Pick a test lead with rich activity data
2. Manually trigger the workflow
3. Confirm the `score` column updated
4. Check the stage moved if score crossed 75
5. Confirm the Slack notification fired (if applicable)

## Troubleshooting

<AccordionGroup>
  <Accordion title="Scores seem random or unchanging">
    Event tracking isn't firing. Verify page visits, email opens, and form submissions are being logged — visit a pricing page yourself, then query the events table. If nothing appears, fix tracking first. Scoring without data produces noise.
  </Accordion>

  <Accordion title="Too many 'hot' leads and sales is overwhelmed">
    Threshold is too low. Raise the hot cutoff from 75 to 85 or 90. Alternative: tighten the point weights — visiting a pricing page once shouldn't count the same as visiting five times over two weeks.
  </Accordion>

  <Accordion title="Sales says the hot leads don't close">
    The scoring model doesn't match your ICP. Pull 50 closed-won deals and 50 closed-lost deals. What signals differ? Rebuild the rules to emphasize those. Firmographics often matter more than behavior — company size and role are usually the strongest predictors.
  </Accordion>

  <Accordion title="Missing signals in the query">
    You're scoring on what you have, not what predicts. Add more tracked events (LinkedIn visits, document views, video watches) and more CRM fields (industry, tech stack, last funding round) to enrich scoring.
  </Accordion>

  <Accordion title="Slack notifications for the same lead multiple times">
    Only notify on *transition* to hot, not on every workflow run for a hot lead. Check the previous score:

    ```
    {{previous_score}} < 75 AND {{computed_score}} >= 75
    ```
  </Accordion>
</AccordionGroup>

## What's Next?

<CardGroup cols={2}>
  <Card title="Cold Email Sequences" icon="envelopes-bulk" href="/how-tos/cold-email">
    Route leads into sequences based on their score
  </Card>

  <Card title="CRM Contacts" icon="address-book" href="/how-tos/crm-contacts">
    Enrich leads with firmographic data for better scoring
  </Card>
</CardGroup>
