
Nextdoor
tap-nextdoor (meltanolabs variant)
Nextdoor is a neighbourhood social network. Nextdoor Ads Manager (NAM) is its self-serve advertising platform, where businesses run campaigns targeted at specific neighbourhoods, postal codes or radii, and measure them with the Nextdoor conversion pixel.
This tap extracts the objects an advertiser manages in NAM - advertisers, campaigns, ad groups, ads, creatives and custom audiences - plus performance reporting, through the Nextdoor Ads API.
Some NAM actions remain UI-only (initial sign-up, payment methods, adding or archiving custom audiences, archiving media assets), so they cannot be extracted.
Available Streams
| Stream | Replication | Replication Key |
|---|---|---|
| users | Full Table | — |
| profiles | Full Table | — |
| advertisers | Full Table | — |
| campaigns | Incremental | updated_at |
| ad_groups | Incremental | updated_at |
| ads | Incremental | updated_at |
| creatives | Incremental | updated_at |
| reports | Full Table | — |
| ad_stats | Full Table | — |
| performance_report | Full Table | — |
| custom_audiences | Incremental | updated_at |
users
The NAM user that owns the access token, and which advertisers they can reach.
| Field | Type | Description |
|---|---|---|
| id | string | The user's ads ID |
| name | string | User's display name |
| email | string | User's email address |
| email_confirmed | boolean | Whether the user has confirmed their email |
| advertisers_with_access | array | Advertisers this user can access, with their role on each |
profiles
The advertising profile behind the token, including its billing profile and whether it is an agency.
| Field | Type | Description |
|---|---|---|
| id | string | The profile's ads ID |
| name | string | Profile name |
| associated_user_ids | array | Users attached to this profile |
| payment_profile_id | string | Billing profile backing this advertising profile |
| is_ad_agency | boolean | Whether the profile represents an agency |
advertisers
Advertiser accounts the token can access. Read from the /me endpoint, since the Ads API has
no advertiser list endpoint, and optionally narrowed with Advertiser IDs.
| Field | Type | Description |
|---|---|---|
| advertiser_id | string | Advertiser ID. Sourced from id in the API response, which the reference docs call advertiser_id. |
| role | string | The token holder's role on this advertiser, e.g. CLIENT_ADMIN |
campaigns
Campaigns, with objective, status and flight dates.
Supports incremental replication using updated_at.
| Field | Type | Description |
|---|---|---|
| id | string | Campaign ID |
| advertiser_id | string | ID of the advertiser that owns the campaign |
| name | string | Campaign name |
| status | string | Effective delivery status, e.g. ACTIVE, PAUSED, ARCHIVED. May differ from user_status when a parent is paused. |
| user_status | string | Status explicitly set by the advertiser |
| objective | string | Campaign objective, e.g. CONVERSION, TRAFFIC |
| sub_objective | string | Objective refinement, e.g. WEBSITE_CONVERSIONS. Undocumented. |
| special_ad_category | boolean | Whether the campaign is in a regulated category (housing, credit, employment). Undocumented. |
| created_at | datetime | When the campaign was created |
| updated_at | datetime | When the campaign was last modified — replication key |
| start_time | datetime | Scheduled start of delivery |
| end_time | datetime | Scheduled end of delivery; absent if open-ended |
ad_groups
Ad groups, carrying the bid, budget, placements, frequency caps and all targeting.
Supports incremental replication using updated_at.
| Field | Type | Description |
|---|---|---|
| id | string | Ad group ID |
| advertiser_id | string | Owning advertiser ID |
| campaign_id | string | Parent campaign ID |
| name | string | Ad group name |
| status | string | Effective delivery status, e.g. ACTIVE, PAUSED_DUE_TO_CAMPAIGN_PAUSE |
| user_status | string | Status explicitly set by the advertiser |
| placements | array | Where ads may serve, e.g. FEED, FSF, RHR |
| audience_network_is_on | boolean | Whether off-Nextdoor audience network delivery is enabled |
| bid | object | Bid settings for the ad group |
| budget | object | Budget settings for the ad group |
| start_time | datetime | Scheduled start of delivery |
| end_time | datetime | Scheduled end of delivery; absent if open-ended |
| frequency_caps | array | Limits on how often one neighbour sees these ads |
| targeting | object | Geographic, audience, interest and daypart targeting |
| custom_audience_ids | array | Custom audience IDs. Documented as a top-level field but not returned by the live API, which nests them under targeting.custom_audience_targeting; both are read. |
| created_at | datetime | When it was created |
| updated_at | datetime | When it was last modified — replication key |
ads
Individual ads, linking an ad group to the creative it renders.
Supports incremental replication using updated_at.
| Field | Type | Description |
|---|---|---|
| id | string | Ad ID |
| advertiser_id | string | Owning advertiser ID |
| adgroup_id | string | Parent ad group ID |
| creative_id | string | Creative rendered by this ad; joins to the creatives stream |
| name | string | Ad name |
| status | string | Effective delivery status, e.g. ACTIVE, INACTIVE, ARCHIVED, INELIGIBLE |
| user_status | string | Status explicitly set by the advertiser |
| created_at | datetime | When the ad was created |
| updated_at | datetime | When the ad was last modified — replication key |
creatives
Creative assets - headline, body, call to action, image and logo URLs, and click and impression trackers.
Supports incremental replication using updated_at.
| Field | Type | Description |
|---|---|---|
| id | string | Creative ID |
| advertiser_id | string | Owning advertiser ID |
| name | string | Creative name |
| status | string | Review status, e.g. APPROVED |
| placement | string | Placement this creative targets |
| creative_type | string | Creative format, e.g. IMAGE_NATIVE_V3. Undocumented. |
| text_overlays | array | Text rendered over the image. Undocumented. |
| advertiser_name | string | Advertiser name shown to neighbours |
| headline | string | Headline text |
| body_text | string | Body copy |
| offer_text | string | Offer text, if any |
| price | string | Displayed price, if any |
| cta | string | Call to action, e.g. Learn more |
| canvas_image_url | string | Main creative image |
| logo_image_url | string | Advertiser logo |
| clickthrough_url | string | Destination URL |
| impression_tracking_urls | array | Third-party impression pixels |
| click_tracking_urls | array | Third-party click trackers |
| created_at | datetime | When it was created |
| updated_at | datetime | When it was last modified — replication key |
reports
Saved and scheduled report definitions with their CSV download URLs. Definitions only - this stream carries no metrics.
| Field | Type | Description |
|---|---|---|
| id | string | Report ID |
| advertiser_id | string | Owning advertiser ID |
| name | string | Report name |
| download_url | string | Presigned S3 URL for the report CSV. Short-lived, and carries embedded AWS credentials - treat as a secret. |
ad_stats
Aggregate performance per ad over the configured window. One row per ad, not a daily time series, and one request per ad, which makes this the slowest stream.
| Field | Type | Description |
|---|---|---|
| ad_id | string | Ad these metrics are for |
| advertiser_id | string | Owning advertiser ID |
| start_time | datetime | Start of the reporting window |
| end_time | datetime | End of the reporting window, inclusive |
| billable_spend | string | Billable spend, currency-prefixed, e.g. "GBP 12.50" |
| cpc | string | Cost per click, currency-prefixed |
| cpm | string | Cost per thousand impressions, currency-prefixed |
| cost_per_result | string | Cost per result, currency-prefixed |
| impressions | integer | Impressions served |
| clicks | integer | Clicks received |
| ctr | number | Click-through rate as a percentage value, e.g. 0.557 means 0.557%. Verified against clicks/impressions on live data. |
| result | number | Results against the campaign objective |
| total_conversions | integer | All conversions, summing the breakdown below |
| purchase_conversions | integer | Purchase conversions |
| lead_conversions | integer | Lead conversions |
| sign_up_conversions | integer | Sign-up conversions |
| add_to_cart_conversions | integer | Add-to-cart conversions |
| initiate_checkout_conversions | integer | Checkout-initiated conversions |
| search_conversions | integer | Search conversions |
| view_content_conversions | integer | View-content conversions |
| add_to_wishlist_conversions | integer | Add-to-wishlist conversions |
| subscribe_conversions | integer | Subscribe conversions |
| other_conversions | integer | Conversions not in the categories above |
performance_report
A custom performance report, defined entirely by the Ad Performance Report setting
and built via the reporting API. Its fields are therefore not fixed: the schema is
generated from your config, with one column per requested dimension, one per requested
metric, plus advertiser_id, report_id and date. See Setup step 4 below for the
available metrics and dimensions, and for the caveats - this is the one stream that
writes to your account.
Leave the setting unset to skip this stream and use ad_stats instead.
custom_audiences
Custom audiences referenced by ad groups. There is no list endpoint, so audiences are fetched by the IDs found on their ad groups.
Supports incremental replication using updated_at.
| Field | Type | Description |
|---|---|---|
| id | string | Custom audience ID |
| advertiser_id | string | Owning advertiser ID |
| adgroup_id | string | The ad group this audience was discovered from |
| name | string | Audience name |
| description | string | Advertiser's own notes |
| audience_type | string | How the audience was built, e.g. emails |
| created_at | datetime | When it was created |
| updated_at | datetime | When it was last modified — replication key |
Setup
1. Generate an access token
Sign in to Nextdoor Ads Manager and generate an Ads API access token. Set it as Access Token - it is sent as a bearer token on every request.
2. Choose which advertisers to extract (optional)
Leave Advertiser IDs empty to extract every advertiser the token can reach. Set it to narrow extraction to specific advertiser accounts, along with their child campaigns, ad groups and ads.
3. Set the reporting window
Start Date and End Date bound the ad_stats and performance_report streams only. Both
accept an ISO-8601 date (2026-01-01) or date-time (2026-01-01T00:00:00Z), and both
default to today. End Date is inclusive.
Every other stream replicates on its own updated_at bookmark or in full, and ignores
these two settings.
4. Define a performance report (optional)
The performance_report stream builds an ad hoc report from the Ad Performance Report
setting:
report:
metrics: [IMPRESSIONS, CLICKS, CTR, SPEND, BILLABLE_SPEND, CPM, CPC, CONVERSIONS]
dimension_granularity: [AD] # CAMPAIGN, AD_GROUP, AD, PLACEMENT
time_granularity: [DAY] # DAY, WEEK, MONTH
name: tap-nextdoor performance report # report name in NAM
stream_name: performance_report # rename the stream if you like
recipient_emails: [] # every sync emails these
campaign_ids: [] # optional filters
adgroup_ids: []
ad_ids: []
Every key except the three granularity/metric lists is optional. The same definition as
JSON, for the Ad Performance Report setting field or the TAP_NEXTDOOR_REPORT
environment variable:
{
"metrics": ["IMPRESSIONS", "CLICKS", "CTR", "SPEND", "BILLABLE_SPEND", "CPM", "CPC", "CONVERSIONS"],
"dimension_granularity": ["AD"],
"time_granularity": ["DAY"],
"name": "ad performance report",
"recipient_emails": []
}
All three enum lists are validated before any request is made, so a typo fails with the supported values listed rather than a bare API error.
Caveats - unlike every other stream, this one writes. Each sync creates a report object in the advertiser's account, and those accumulate; the
reportsstream lists every one created so far. Each sync also emails everyone inrecipient_emails- leave it empty to skip the email. Report rows carry no IDs, onlyCampaign Name,Ad Group NameandAd Name, so they join to thecampaigns,ad_groupsandadsstreams by name only; renaming an entity in NAM breaks that join.
Leave the setting unset to skip the stream and use ad_stats instead, which is
side-effect free but returns a single aggregate row per ad rather than a daily time
series, at a cost of one request per ad.
5. Tune pagination (optional)
Page Size sets how many records are requested per page from the list endpoints. It defaults to 100.
Data notes
Money is always returned currency-prefixed ("GBP 3.35") on bids, budgets and all stats
spend fields, so those fields are typed as strings rather than parsed, and no currency
information is lost.
CTR is expressed as a percentage value in both performance streams - 1.05 means 1.05%.
Campaign and ad group timestamps arrive with a bracketed zone ID
(2025-08-26T00:01:34+01:00[Europe/London]), which is invalid against the JSON Schema
date-time format. The tap strips the zone ID and keeps the UTC offset, so the instant
is unchanged.
Settings
Access Token
Ads API access token, generated in Nextdoor Ads Manager. Sent as a bearer token on every request.
Advertiser IDs
Advertisers to extract data for, by ID, along with their child campaigns, ad groups and ads. Leave empty to extract every advertiser the access token can reach.
Start Date
Start of the reporting window for the performance_report and ad_stats streams. Accepts an ISO-8601 date-time (2026-01-01T00:00:00Z) or a plain date (2026-01-01); the API takes whole days, so any time component is truncated. Defaults to today.
End Date
End of the reporting window, inclusive. Accepts an ISO-8601 date-time (2026-01-31T23:59:59Z) or a plain date (2026-01-31). Defaults to today.
Ad Performance Report
Definition of the custom report built by the performance_report stream. Keys: metrics, dimension_granularity, time_granularity, name, stream_name, recipient_emails, campaign_ids, adgroup_ids, ad_ids. Set stream_name to match the chosen granularity, e.g. campaign_performance_report. NOTE: each sync creates a report in the advertiser's account and emails it to recipient_emails.
Nextdoor connector is available on Meltano. It is built, maintained, supported, and tested by Meltano.