Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 8 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -534,7 +534,8 @@ dm properties export --body '{"locations": [...]}' --mobile-only --json

#### `dm people search`

Search people with filters and locations.
Build an audience of people using demographic, property, contact, and location filters. This command
does not accept a person's name as a filter. Use `dm enrich name` for a specific person by name.

```bash
dm people search --body '{
Expand Down Expand Up @@ -693,20 +694,25 @@ dm enrich phone -f phones.csv --include-properties --fields estimated_value

#### `dm enrich name [name]`

Look up people by name. Supports "First Last" or just "Last" format.
Look up a specific person by name. Supports "First Last" or just "Last" format. People Search does
not have a name filter, so use this command whenever the input is a person's name.

```bash
dm enrich name "Jane Doe"
dm enrich name "Jane Doe" --state TX --estimate-cost
dm enrich name "Doe" --state TX --page 2
dm enrich name "Jane Doe" --zip 78704 --include-properties
dm enrich name "Jane Doe" --fields estimated_household_income,estimated_value
dm locations search -q "Austin" --type city --state TX --json
dm enrich name "Jane Doe" --city 7333 --estimate-cost
```

| Option | Description |
| ---------------------- | ----------------------------- |
| `--state <code>` | Narrow by state |
| `--zip <code>` | Narrow by ZIP code |
| `--county <fips>` | Narrow by county FIPS |
| `--city <place-id>` | Narrow by city place ID |
| `--include-properties` | Include associated properties |
| `--fields <csv>` | Field IDs from `dm fields` |
| `--estimate-cost` | Preview count and credits |
Expand Down
19 changes: 16 additions & 3 deletions playbook/PLAYBOOK.md
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,11 @@ If a command fails due to auth, tell the user to run `dm login` in their termina

### State DM3: People Search

**Symptoms:** User wants to find people (owners, renters, residents) matching criteria.
**Symptoms:** User wants to find an audience of people (owners, renters, residents) matching demographic, property, contact, or location criteria.

**Routing boundary:** Do not use this state when the user provides a specific person's name. People
Search has no name filter. Route a known name to State DM5 and use `dm enrich name`.

**Key Questions:**

- Are you looking for property owners, renters, or residents?
Expand Down Expand Up @@ -153,15 +157,22 @@ If a command fails due to auth, tell the user to run `dm login` in their termina
### State DM5: Person Enrichment

**Symptoms:** User has a name, phone, or email and wants to find the person.

**Routing boundary:** A specific name always uses person enrichment, not People Search. Use
`dm enrich name` or `dealmachine_enrich_name`. Narrow with a state, ZIP code, county, or city place
ID when available. For a city name, run
`dm locations search -q "<city>" --type city --state <state> --json`, then pass the result's `code`
to `dm enrich name --city <place-id>`.

**Key Questions:**

- What identifier do you have? (name, phone, email)
- For name searches: do you know their state or ZIP? (narrows results, saves credits)
- For name searches: do you know their state, ZIP, county, or city? (narrows results, saves credits)
- Do you need their associated properties?
**Interventions:**
- `dm enrich phone "5551234567"`
- `dm enrich email "john@example.com"`
- `dm enrich name "John Smith" --state TX`
- `dm enrich name "John Smith" --state TX --estimate-cost`
- Add `--include-properties` if property data needed

### State DM6: Address Validation
Expand Down Expand Up @@ -600,6 +611,8 @@ dm enrich phone "5551234567" --include-properties
dm enrich name "John Smith"
dm enrich name "John Smith" --state TX
dm enrich name "John Smith" --zip 78704
dm locations search -q "Austin" --type city --state TX --json
dm enrich name "John Smith" --city 7333 --estimate-cost
dm enrich name "Smith" # Last name only
dm enrich name "John Smith" --include-properties
```
Expand Down
6 changes: 6 additions & 0 deletions scripts/validate-agent-plugin.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,12 @@ assert.deepEqual(mcp.mcpServers.dealmachine, {

assert.match(skill, /^---\nname: dealmachine\n/, 'DealMachine skill front matter is missing');
assert.match(skill, /\ndescription: .+\n/, 'DealMachine skill description is missing');
assert.match(
skill,
/People Search builds audiences[\s\S]+it has no name filter/,
'DealMachine skill must distinguish People Search from person-name enrichment'
);
assert.match(skill, /dealmachine_enrich_name/, 'DealMachine skill must route names to enrichment');

const demoVideoPath = resolve(packageRoot, 'assets/plugin-demo/dealmachine-agent-plugin-demo.mp4');
const demoVideo = await stat(demoVideoPath);
Expand Down
6 changes: 6 additions & 0 deletions skills/dealmachine/REFERENCE.md
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,12 @@ Use these exact Tool IDs. Do not pluralize `property`.

People export is available through the CLI.

People Search builds audiences from demographic, property, contact, and location filters. It has no
person-name filter. For a specific person by name, use `dealmachine_enrich_name` or
`dm enrich name`. For city narrowing, resolve the city with `dealmachine_location_search` or
`dm locations search -q "Austin" --type city --state TX --json`, then pass its `code` as the city
place ID.

### Enrichment

- `dealmachine_enrich_address`
Expand Down
23 changes: 21 additions & 2 deletions skills/dealmachine/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,22 @@ Identify:

Ask one focused question only when a missing detail would materially change the search or credit cost.

## Choose the correct people workflow

| User intent | Correct workflow |
| --- | --- |
| Find a specific person by name | `dealmachine_enrich_name` or `dm enrich name` |
| Find a specific person by email or phone | Use the matching enrichment MCP Tool or CLI command |
| Find an audience using demographic, property, contact, or location criteria | `dealmachine_people_search` or `dm people search` |
| Fetch a known DealMachine person ID | `dealmachine_people_get` or `dm people get` |

Do not search the People Search filter catalog for a person's name. People Search builds audiences
from filters and locations, and it has no name filter. Name enrichment accepts first and last name
with an optional state, ZIP code, county, or city place ID. Resolve a city name with
`dealmachine_location_search` or `dm locations search`, then use the result's `code` for the name
lookup. For broad name matches, use `estimate_cost: true` with the MCP Tool or `--estimate-cost`
with the CLI before retrieving records.

## Use MCP tools

### Discovery
Expand All @@ -70,14 +86,17 @@ Ask one focused question only when a missing detail would materially change the
### People workflows

- Use `dealmachine_people_count` before a broad search.
- Use `dealmachine_people_search` for results and the matching get tools for known IDs.
- Use `dealmachine_people_search` only for an audience defined by filters and locations. It does not
accept a person's name as a filter.
- Use the matching get tools for known DealMachine person IDs.
- People search and lookup are available through MCP. Use the CLI for a people export.

### Enrichment

- Use the address, latitude and longitude, or APN enrichment tool for a property.
- Use the email, phone, or name enrichment tool for a person.
- Narrow name searches with a location.
- A specific person's name always uses `dealmachine_enrich_name` or `dm enrich name`.
- Narrow name searches with a state, ZIP code, county, or city place ID.

## Use the CLI

Expand Down
8 changes: 8 additions & 0 deletions src/commands/agents.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,14 @@ dm agents playbook
- Check auth with \`dm whoami --verify --json\`. If auth fails, ask the user to run \`dm login\`.
- Use request files or stdin for structured bodies instead of hand-editing long shell strings.

## People Lookup Routing

- A specific person by name uses \`dm enrich name\`. People Search does not have a name filter.
- A specific person by email or phone uses the matching \`dm enrich\` command.
- \`dm people search\` is only for audiences defined by demographic, property, contact, or location filters.
- A known DealMachine person ID uses \`dm people get\`.
- Name enrichment supports an optional state, ZIP code, county, or city place ID. Resolve a city with \`dm locations search\`, then pass its \`code\` to \`dm enrich name --city\`.

## Credit-Safe Workflow

1. Discover live filters and fields before searches:
Expand Down
10 changes: 10 additions & 0 deletions tests/commands/agents.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,12 @@ describe('agent commands', () => {

expect(log).toHaveBeenCalledWith(expect.stringContaining('dm agents playbook'));
expect(log).toHaveBeenCalledWith(expect.stringContaining('Credit-Safe Workflow'));
expect(log).toHaveBeenCalledWith(
expect.stringContaining('A specific person by name uses `dm enrich name`')
);
expect(log).toHaveBeenCalledWith(
expect.stringContaining('People Search does not have a name filter')
);
});

it('prints agent guidance as JSON', async () => {
Expand All @@ -27,6 +33,7 @@ describe('agent commands', () => {
recommended_first_command: 'dm agents playbook',
});
expect(payload.content).toContain('DealMachine CLI Agent Guide');
expect(payload.content).toContain('A specific person by name uses `dm enrich name`');
});

it('prints the DealMachine Playbook as JSON', async () => {
Expand All @@ -40,5 +47,8 @@ describe('agent commands', () => {
type: 'playbook',
});
expect(payload.content).toContain('DealMachine Playbook: Natural Language Property Intelligence');
expect(payload.content).toContain(
'A specific name always uses person enrichment, not People Search.'
);
});
});