email-search
$
npx mdskill add extruct-ai/gtm-skills/email-searchVerify emails and phones for LinkedIn contacts instantly.
- Converts LinkedIn profiles into verified contact details.
- Integrates with Prospeo and Fullenrich enrichment providers.
- Processes people-search table IDs to retrieve contact data.
- Outputs structured CSV files ready for email generation.
SKILL.md
.github/skills/email-searchView on GitHub ↗
---
name: email-search
description: >
Get verified emails and phones for contacts found by people-search.
Takes LinkedIn profiles from the Extruct people table and enriches them
via contact enrichment providers like Prospeo or Fullenrich. Supports single-provider and waterfall modes.
Outputs a contact CSV ready for email-generation.
Triggers on: "get emails", "find emails", "enrich contacts", "email finder",
"get phone numbers", "enrich people", "contact enrichment", "verify emails",
"email enrichment".
---
# Email Finder
Turn LinkedIn profiles into verified emails and phones. Takes the output of `people-search` and runs it through contact enrichment providers like Prospeo or Fullenrich.
## Related Skills
```
list-segmentation → people-search → email-search → email-generation → email-response-simulation → campaign-sending
```
After `people-search` finds WHO to contact (with LinkedIn URLs), this skill gets their verified contact info.
## Extruct API Operations
This skill delegates all Extruct API calls to the `extruct-api` skill.
For all Extruct API operations, read and follow the instructions in `skills/extruct-api/SKILL.md`.
The only Extruct operation in this skill is reading people table data. Contact enrichment uses separate providers (Prospeo, Fullenrich, etc.) with their own APIs.
## Inputs
| Input | Source | Required |
|-------|--------|----------|
| People table ID | Child table from `people-search` | yes (or CSV) |
| People CSV | `claude-code-gtm/csv/input/{campaign}/people_linkedin.csv` | yes (or table) |
| Provider preference | User choice | yes |
| Include mobile phones | User choice | no (default: no) |
## Choosing a Provider
Ask the user which contact enrichment provider they want to use. If they need guidance, consider:
- **Have LinkedIn URLs?** → providers with LinkedIn enrichment work best
- **Need highest email hit rate?** → waterfall providers try multiple sources
- **Budget-conscious?** → check credit costs per match
- **Need mobile phones?** → confirm the provider covers phone data
- **Want maximum coverage?** → run one provider first, then a second for misses
If the user doesn't know where to start, pre-configured options with local reference docs are available in [references/](references/).
## Workflow
### Step 0: Confirm provider and learn API
1. Ask the user which contact enrichment provider they want to use
2. Fetch or read the provider's API documentation and identify:
- Enrichment endpoint (single and bulk)
- Required input fields (LinkedIn URL, name, domain, etc.)
- Authentication method and credentials
- Throughput limits and request constraints
- Response format (email, phone, verification status)
- Credit/pricing model
3. Ask for their API credentials and confirm access
4. Plan the implementation and confirm with the user before proceeding
### Step 1: Load people data
**Option A: From Extruct people table (recommended)** — Use the extruct-api skill to fetch data from the people table. Extract `full_name`, `profile_url`, `role`, and `parent_row_id` from each row. Split full name into first/last.
**Option B: From CSV** — Read `claude-code-gtm/csv/input/{campaign}/people_linkedin.csv`.
### Step 2: Check credits
Before running enrichment, check the user's available credits or quota with the chosen provider (using the endpoint identified in Step 0). Present a cost estimate based on the number of contacts to enrich.
### Step 3: Run enrichment
Using the chosen provider's API (from Step 0):
1. Prepare contact data in the format the provider expects (LinkedIn URL, name + domain, etc.)
2. Submit contacts in batches according to the provider's rate limits
3. Handle async responses if the provider uses polling
4. Collect results: emails, phone numbers, verification status
5. Track matched vs. unmatched contacts
If the user wants a **waterfall** (two providers), run the first provider, collect misses, then run misses through the second.
### Step 4: Deduplicate and clean
Deduplicate by email. Filter out:
- Entries with no email
- Results where the provider marks verification as invalid
### Step 5: Output contact CSV
Save enriched contacts to `claude-code-gtm/csv/input/{campaign}/contacts.csv` with columns:
- `first_name`, `last_name`, `email`, `email_verified`, `job_title`, `company_name`, `domain`, `linkedin_url`, `phone`, `location`, `source`
### Step 6: Review with user
Present summary:
```
Enrichment Results:
- Contacts submitted: N
- Emails found: N (X% hit rate)
- Emails verified: N
- Phones found: N
- No match: N
- Provider: [chosen provider]
```
Show a sample of 10 contacts for spot-checking:
| Name | Title | Company | Email | Phone | Source |
|------|-------|---------|-------|-------|--------|
| ... | ... | ... | ... | ... | ... |
Ask:
- "Hit rate look acceptable? (>60% is good, >80% is great)"
- "Want to run the misses through another provider?"
- "Ready to proceed to `email-generation`?"
## API References
Pre-configured provider docs in [references/](references/) directory. For other providers, docs are fetched during Step 0.
More from extruct-ai/gtm-skills
- campaign-sending>
- competitor-monitoring>
- context-building>
- email-generation>
- email-prompt-building>
- email-response-simulation>
- email-verification>
- enrichment-design>
- extruct-apiRun explicit Extruct API tasks through the bundled Extruct CLI. Covers Deep Search, semantic search, lookalike search, company and people tables, column operations, enrichment, and contact finding.
- hypothesis-building>