Creating a Reverse ETL Sync
This guide walks you through creating a reverse ETL sync in Zeotap. A reverse ETL sync connects a model to a destination, maps fields, and runs on a schedule to keep your destination data up to date.
Prerequisites
Before creating a reverse ETL sync, you need:
- A configured Model with column types and a primary key set
- A configured Destination with valid authentication
- Appropriate workspace permissions (Admin or Editor role)
Step-by-Step Guide
Step 1: Navigate to Reverse ETL
- Log in to your Zeotap workspace
- Click Reverse ETL in the left sidebar
- Click the Create Reverse ETL Sync button
Step 2: Name Your Reverse ETL Sync
Give the reverse ETL sync a descriptive name that identifies the data, destination, and cadence:
- “CRM Contacts - Hourly”
- “Google Ads Audience - Daily”
- “HubSpot Lifecycle Sync”
- “Salesforce Leads from Marketing DB”
Step 3: Select a Model
Choose the model that provides the data for this reverse ETL sync. The dropdown shows all available models with their source and column count.
When you select a model, Zeotap displays the model’s columns and their types (identifier vs. attribute) so you can plan your field mapping.
Step 4: Select a Destination
Choose the destination where you want to send the data. The dropdown shows all configured destinations with their type and health status.
After selecting a destination, Zeotap loads the destination’s available objects and fields. Depending on the destination type, you may need to:
- Select an object — For CRM destinations (Salesforce, HubSpot), choose the object type to sync to (e.g., Contact, Lead, Account)
- Select a list or audience — For advertising destinations (Google Ads, Meta Ads), choose or create the target audience list
- Confirm the endpoint — For webhook or API destinations, confirm the target URL
Step 5: Choose a Reverse ETL Sync Mode
Select how Zeotap should handle data at the destination:
| Mode | When to Use |
|---|---|
| Upsert | You want to create new records and update existing ones, but never delete. This is the safest and most common mode. |
| Mirror | You want the destination to be an exact copy of the model results. Records not in the model are deleted from the destination. |
| Append | You only want to add new records. Existing records are never updated or deleted. Good for event/log data. |
See Sync Modes for detailed explanations of each mode.
Step 6: Map Fields
Map columns from your model to fields in the destination. This step is where you connect your data to the destination’s schema.
For each destination field, select the corresponding model column:
| Model Column | → | Destination Field |
|---|---|---|
email | → | |
first_name | → | FirstName |
last_name | → | LastName |
lifetime_value | → | LTV__c (custom field) |
segment | → | Segment__c (custom field) |
Identifier mapping: At least one model column marked as an identifier must be mapped to the destination’s primary identifier field (e.g., Email for Salesforce Contacts). This is how Zeotap matches source records to destination records for upsert and mirror operations.
Required fields: Some destinations have required fields (e.g., Salesforce requires LastName for Contacts). These are marked in the mapping interface and must be mapped.
See Field Mapping for the full guide.
Step 7: Set a Schedule
Configure when the reverse ETL sync should run:
Interval-based:
- Every 15 minutes
- Every 30 minutes
- Every hour
- Every 6 hours
- Every 12 hours
- Every 24 hours
Cron-based:
- Custom cron expression for precise timing
- Example:
0 9 * * 1-5(9 AM on weekdays)
Manual only:
- No automatic schedule — run the sync manually when needed
See Scheduling for details on cron syntax and best practices.
Step 8: Review and Save
Review the complete reverse ETL sync configuration:
- Model and its columns
- Destination and target object
- Sync mode
- Field mapping
- Schedule
Click Save to create the reverse ETL sync. If you configured a schedule, the first run will be triggered at the next scheduled time.
Step 9: Run the First Reverse ETL Sync (Optional)
After saving, you can trigger an immediate manual run to verify everything works:
- Click Run Now on the sync detail page
- Watch the sync run progress in real-time
- Review the results — rows processed, created, updated, errors
- Fix any issues before the scheduled runs begin
Using the API
Create a reverse ETL sync programmatically:
curl -X POST https://composable.zeotap.com/api/v1/syncs \
-H "Authorization: Bearer $API_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "CRM Contacts - Hourly",
"model_id": "mod_abc123",
"destination_id": "dst_xyz789",
"destination_object": "Contact",
"mode": "upsert",
"schedule": {
"type": "interval",
"interval_minutes": 60
},
"field_mappings": [
{
"source_column": "email",
"destination_field": "Email",
"is_identifier": true
},
{
"source_column": "first_name",
"destination_field": "FirstName"
},
{
"source_column": "last_name",
"destination_field": "LastName"
},
{
"source_column": "lifetime_value",
"destination_field": "LTV__c"
}
]
}'Trigger a Manual Run
curl -X POST https://composable.zeotap.com/api/v1/syncs/{sync_id}/trigger \
-H "Authorization: Bearer $API_TOKEN"Editing a Reverse ETL Sync
To modify an existing reverse ETL sync:
- Navigate to Reverse ETL in the sidebar
- Click on the sync to edit
- Update the configuration (field mapping, schedule, sync mode, etc.)
- Click Save
Changes take effect on the next sync run. In-progress runs are not affected.
Considerations when editing:
- Changing the model may require updating field mappings
- Changing the sync mode affects how records are handled (e.g., switching from upsert to mirror enables deletes)
- Changing the schedule takes effect immediately
Pausing and Resuming
Pause a Reverse ETL Sync
To temporarily stop a reverse ETL sync without deleting it:
- Navigate to the reverse ETL sync detail page
- Click Pause
Paused reverse ETL syncs do not run on schedule, but their configuration and run history are preserved.
Resume a Reverse ETL Sync
- Navigate to the paused reverse ETL sync
- Click Resume
The reverse ETL sync resumes on its configured schedule. If a scheduled run was missed while paused, it will not run retroactively — the next run occurs at the next scheduled time.
Deleting a Reverse ETL Sync
- Navigate to Reverse ETL in the sidebar
- Click on the reverse ETL sync to delete
- Click Delete and confirm
Deleting a reverse ETL sync removes the configuration and run history. Data already sent to the destination is not affected — Zeotap does not “unsync” data from destinations.
Common Issues
| Issue | Solution |
|---|---|
| ”No identifier mapped” | Map at least one model identifier column to the destination’s primary identifier field |
| ”Required field not mapped” | Map all required destination fields (shown with an asterisk) |
| First run shows 0 rows | Verify the model query returns data by previewing it |
| All rows show as errors | Check the error details — often a data format mismatch or missing required field |
| Reverse ETL sync created but not running | Verify the schedule is set (not “manual only”) or trigger a manual run |
Next Steps
- Configure field mapping in detail
- Set up scheduling with cron expressions
- Understand sync modes to choose the right behavior
- Monitor sync runs for ongoing performance