1. Webhooks
  • Synup Local SEO API - Getting Started
  • Locations
    • Location Attributes
      MARKDOWN
    • Photo specifications for your business location
      MARKDOWN
    • Star and Unstar Photos
      MARKDOWN
    • Create a new business location
      POST
    • Update business location
      POST
    • List all locations
      GET
    • List particular locations
      GET
    • Search locations
      GET
    • Get locations by store codes
      GET
    • Get Photos by Location IDs
      GET
    • Upload Photos to a Location
      POST
    • Check Bulk Photo Upload Status
      GET
    • Star/Unstar Location Photos
      POST
    • Delete Location Photos
      POST
    • Archive multiple locations
      POST
    • Cancel scheduled location archival
      POST
    • Activate archived locations
      POST
    • List Active Subscriptions
      GET
    • Get a list of supported countries and their states
      GET
    • Get SubCategories and AdditionalCategories
      GET
    • Get Site Details for Your Plan
      GET
    • Location Indexing Rate
      GET
    • Available advanced filter values
      GET
    • Download locations
      GET
    • Filter locations
      GET
    • Google verification location stats
      GET
    • Location add-on count
      GET
    • Location package count
      GET
    • Available search filter values
      GET
  • Organizing locations
    • Organizing locations
    • Create a new folder
    • List all folders
    • List all folders under an account in hierarchical structure
    • Get details of a folder
    • Rename a folder
    • Add locations to a folder
    • Remove locations from a folder
    • Delete a folder
    • List locations under a folder
    • List all tags
    • List locations by tags
    • Add location to a tag
    • Remove location from a tag
    • Default folder
  • User Management
    • User Attributes
    • Create User with Role
    • List Users
    • List Users by ID
    • Add Locations to User
    • Add User and folder
    • List User Roles
    • Add folders to user
    • List User Resources
    • Update a User
    • Remove Folders for User
    • Remove Locations for User
  • Grid Rank
    • Local Rank Grid
    • Create Rank Grid Report
    • Fetch All Grid Reports for Location
    • Fetch Rank Grid Report By ID
  • Review Campaigns
    • Review Campaign Info Attributes
    • Create a review campaign
    • Add customers to a review campaign
    • List review campaigns
    • List review campaign customers
  • Listings
    • Listings
    • Listing Status Webhooks
    • Get premium listings
    • Get voice listings for a location
    • Get duplicate listings for a location
    • Get all duplicate listings for an account
    • Mark listings as duplicates
    • Mark listings as not duplicates
    • Get AI listings
  • Connected Accounts
    • Connected Accounts
    • Connect Google Profile to Account
    • Connect Facebook Page to Account
    • Bulk connect link for Apple
    • List all connected accounts
    • List folders under a Google account
    • Create GMB Listing
    • Disconnect GMB Profile
    • Disconnect Facebook Account
    • Fetch Connected Account Details
    • Trigger New Matches
    • List Connection Suggestions
    • Fetch Connected Account Listings
    • Confirm Connected Account Matches
    • Connect a location with a listing of a connected account
    • Disconnect Location from Listing
    • create location from connected account listing
    • Apple confirmed matches
    • Connect link for Apple
    • Renew connect link for Apple
  • Rankings
    • Rankings Analytics Attributes
    • Add keywords
    • List Keywords
    • Get keywords performance
    • Archive a keyword
    • Get Rollup Keyword Performance
    • Get Rankings Distribution By Time
  • Profile Analytics
    • Profile Analytics
    • Get Bing Analytics
    • Get Facebook Page Analytics
    • Get Google My Business Analytics
  • Reviews
    • Reviews
    • Review Sources
      • Get a list of interaction sources for location
      • Get a list of interaction sources for account
      • Add / Edit interaction source
    • Fetch all interactions
    • List Interactions by IDs
    • Respond to an Interaction
    • Edit Response for Interaction
    • Archive Response for Interaction
    • Get Interaction Analytics
    • Add Review Widget
    • Edit Review Widget
    • Rollup Review API
  • Automations
    • Temporary Close Location with a reopening date
  • Error Codes
    • ERROR CODES
  • Social
    • Social Overview
    • Create a brand
    • Assign a user to a single brand
    • Assign multiple brands
  • Posts
    • Posts Overview
    • Create an Announcement post
    • Create an Event post
    • Create an Offer post
    • Fetch posts for a location
    • Get a single post
    • Delete a post
    • Create a bulk post
    • Fetch a bulk post by ID
    • Fetch bulk posts for a location
  • Menus
    • Menus Overview
    • Create a menu
    • Fetch menus for a location
    • Add an item to an existing section
    • Update menu currency
    • Assign a menu to a location
  • MCP Server
    • Synup MCP — Getting Connected
    • Synup MCP — Putting It to Work
  • Local Post Ideas
    • Refresh local ideas
    • Suggest local posts for date
    • Analyze reference image
    • Archive local idea
    • Archive local series
    • Branch local chat session
    • Close local chat session
    • Generate all local series posts
    • Generate local holiday idea variant
    • Generate local series post
    • Local active chat session
    • Local calendar
    • Local chat history
    • Local chat sessions
    • Local content series detail
    • Local content series list
    • Local extended config
    • Local holiday idea variants
    • Local idea job status
    • Local image credits
    • Local location info
    • Local observances
    • Local observances with ideas
    • Local pipeline status
    • Local post idea
    • Local post idea counts
    • Local post ideas
    • Local reference images
    • Local scraped context
    • Regenerate local idea
    • Regenerate local idea content
    • Regenerate local idea image
    • Schedule local series
    • Scrape location
    • Send local chat message
    • Set location image credits
    • Start local chat session
    • Switch local chat mode
    • Trigger local pipeline
    • Update local idea
    • Upsert extended location config
  • Social Post Ideas
    • Active chat session
    • Analyze reference image
    • Archive idea
    • Archive series
    • Branch chat session
    • Brand info
    • Calendar
    • Chat history
    • Chat sessions
    • Close chat session
    • Content series detail
    • Content series list
    • Create content series
    • Extended brand config
    • Generate all series posts
    • Generate calendar day
    • Generate holiday idea variant
    • Generate idea visual
    • Generate observance idea
    • Generate series post
    • Holiday idea variants
    • Idea job status
    • Image credits
    • Link post idea to social post
    • Observances
    • Observances with ideas
    • Pipeline status
    • Post idea
    • Post idea counts
    • Post ideas
    • Reference images
    • Refresh ideas
    • Regenerate idea
    • Regenerate idea content
    • Regenerate idea image
    • Schedule series
    • Scrape brand
    • Scraped brand context
    • Send chat message
    • Series posts
    • Set brand image credits
    • Start chat session
    • Suggest posts for date
    • Switch chat mode
    • Trigger pipeline
    • Update extended brand config
    • Update idea
  • Webhooks
    • Synup Webhooks
    • Webhooks
      • Listing connected
      • Listing disconnected
      • Listing re-authorization required
      • Listing became inaccessible
      • Google verification passed
      • Google verification failed
      • Location created
      • Location updated
      • Location deleted
      • Share-of-Voice snapshot completed
      • Grid rank report ready
      • Daily review analytics snapshot
      • Weekly review analytics snapshot
      • Review campaign sent
      • Campaign recipients added
      • Campaign message status changed
      • Campaign feedback submitted
      • Campaign message send rejected
      • Review posted (campaign-attributed)
      • Social post created
      • Social post published
      • Social post deleted
      • Social post rejected
      • Social post failed
      • Boost created
      • Boost active
      • Boost rejected
      • Boost stopped
      • Social channel connected
      • Social channel disconnected
      • Social channel archived
      • Ad account status changed
      • AI post idea generated
      • AI idea scheduled as post
      • AI idea series completed
      • AI idea scrape completed
      • AI idea scrape failed
      • AI idea image generated
      • AI idea image generation failed
    • Endpoint verification handshake
  • Schemas
    • Schemas
      • FolderSchema
        • Schemas
          • ListFoldersResponse
          • FolderInfo
      • LocationResponseSchema
      • LocationResponseErrorSchema
      • SubCategory
      • SubscriptionsResponse
      • CreateFolderRequest
      • FolderNode
      • ListingsResponse
      • LocationListResponse
      • ConnectGoogleInput
      • ConnectFacebookInput
      • DisconnectGoogleRequest
      • TriggerMatchesRequest
      • FetchListingsRequest
      • ConfirmMatchesRequest
      • ConnectListingRequest
      • DisconnectListingRequest
      • ConnectedAccountDetailsResponse
      • ConnectionSuggestionsResponse
      • Keyword
      • Keyword
      • Keyword
      • UnauthorizedError
      • UnauthorizedError
      • UnauthorizedError
      • UnauthorizedError
      • InsightMetric
      • InsightMetric
      • CreateGridReportInput
      • AllGridReportsResponse
      • GridReportResponse
      • CreateUserInput
      • UsersResponse
      • UsersResponse
      • UsersByIdsResponse
      • AnalyticsOverview
      • Interaction
      • Interaction
      • InteractionsResponse
      • ResponseInteraction
      • AddLocationsInput
      • UserRole
      • UserRole
      • CreateReviewCampaignRequest
      • ReviewCampaignsResponse
      • ReviewCampaignCustomersResponse
      • PremiumListing
      • Subscription
      • CreateFolderResponse
      • Listing
      • ConnectGoogleResponse
      • ConnectFacebookResponse
      • DisconnectGoogleResponse
      • ConnectedAccount
      • TriggerMatchesResponse
      • ConfirmMatchesResponse
      • ConnectListingResponse
      • DisconnectListingResponse
      • Error
      • Error
      • BadRequestError
      • BadRequestError
      • BadRequestError
      • NotFoundError
      • UnauthorizedError
      • UnauthorizedError
      • CreateGridReportResponse
      • GridReport
      • GridReport
      • CreateUserResponse
      • PageInfo
      • PageInfo
      • UserDetail
      • AnalyticsTimeline
      • Response
      • Response
      • PageInfo
      • AddLocationsResponse
      • Pagination
      • Pagination
      • CustomerInput
      • ReviewCampaign
      • ReviewCampaignInfo
      • Tag
      • SearchResponse
      • LocationPhoto
      • CustomAttribute
      • Folder
      • Site
      • ConnectedAccountsResponse
      • LocationListing
      • ListingRecord
      • ConnectionSuggestion
      • NotFoundError
      • NotFoundError
      • RankPoint
      • RankPoint
      • CreatedUser
      • UserEdge
      • UserEdge
      • SiteWiseAnalytics
      • InteractionEdge
      • LocationAddStatus
      • LandingPageTemplate
      • EmailTemplate
      • ReviewCampaignCustomer
      • LocationEdge
      • FetchListingsResponse
      • LocationInfo
      • User
      • User
      • MetricWithDelta
      • Interaction
      • EmailTemplate
      • SmsTemplate
      • SuggestedLocationInfo
      • SMSTemplate
      • CampaignStat
      • ReviewSite
      • BusinessHours
      • AddCustomersRequest
    • Business hours
    • paymentMethods
    • Contact Support
    • AppleOauthBulkRequest
    • AddKeywordRequest
    • AppleConfirmedMatches
    • AppleOauthRequest
    • AppleRenewOauthRequest
    • LocationAdvancedSearchFilterType
    • DownloadLocationsInBulkType
    • LocationSummaryConnectionType
    • GoogleVerificationLocationStats
    • LocationAddOnCount
    • LocationPackageCount
    • LocationSearchFilterType
    • DefaultFolderType
    • ReferenceImageAnalysis
    • ArchiveLocalIdeaRequest
    • ArchiveLocalSeriesRequest
    • BranchLocalChatSessionRequest
    • CloseLocalChatSessionRequest
    • GenerateAllLocalSeriesPostsRequest
    • GenerateLocalHolidayIdeaVariantRequest
    • GenerateLocalSeriesPostRequest
    • LocalCalendarDay
    • LocalContentSeries
    • ExtendedLocationConfig
    • LocalIdeaJobStatus
    • LocalLocationInfo
    • LocalObservance
    • LocalObservanceWithIdea
    • LocalPipelineStatus
    • LocalPostIdea
    • ReferenceImageOption
    • PostIdeaCounts
    • ScrapedLocationContext
    • RefreshLocalIdeasRequest
    • RegenerateLocalIdeaRequest
    • RegenerateLocalIdeaContentRequest
    • RegenerateLocalIdeaImageRequest
    • ScheduleLocalSeriesRequest
    • ScrapeLocationRequest
    • SendLocalChatMessageRequest
    • SetLocationImageCreditsRequest
    • StartLocalChatSessionRequest
    • SuggestLocalPostsForDateRequest
    • SwitchLocalChatModeRequest
    • TriggerLocalPipelineRequest
    • UpdateLocalIdeaRequest
    • UpsertExtendedLocationConfigRequest
    • ArchiveIdeaRequest
    • ArchiveSeriesRequest
    • BranchChatSessionRequest
    • BrandInfo
    • CalendarDay
    • CloseChatSessionRequest
    • ContentSeries
    • CreateContentSeriesRequest
    • ExtendedBrandConfig
    • GenerateAllSeriesPostsRequest
    • GenerateCalendarDayRequest
    • GenerateHolidayIdeaVariantRequest
    • GenerateIdeaVisualRequest
    • GenerateObservanceIdeaRequest
    • GenerateSeriesPostRequest
    • LocationConnectedEvent
    • IdeaJobStatus
    • ImageCredits
    • LinkPostIdeaToSocialPostRequest
    • Observance
    • ObservanceWithIdea
    • PipelineStatus
    • PostIdea
    • RefreshIdeasRequest
    • RegenerateIdeaRequest
    • RegenerateIdeaContentRequest
    • RegenerateIdeaImageRequest
    • ScheduleSeriesRequest
    • ScrapeBrandRequest
    • ScrapedBrandContext
    • SendChatMessageRequest
    • SetBrandImageCreditsRequest
    • StartChatSessionRequest
    • SuggestPostsForDateRequest
    • SwitchChatModeRequest
    • TriggerPipelineRequest
    • UpdateExtendedBrandConfigRequest
    • UpdateIdeaRequest
    • AppleOauthBulkPayload
    • CoordinateInput
    • AppleConfirmedMatch
    • AppleOauthPayload
    • AppleRenewOauthPayload
    • LocationSummaryEdge
    • AddOnCount
    • SitePublisherCategory
    • LocalMutationResponse
    • LocalChatSessionResponse
    • LocalGenerateIdeasResponse
    • LocalRegenerateResponse
    • LocalImageCredits
    • LocalTriggerPipelineResponse
    • LocalScheduleSeriesResponse
    • LocalChatMessageResponse
    • MutationResponse
    • ChatSessionResponse
    • GenerateAllSeriesPostsResponse
    • RegenerateResponse
    • LinkPostIdeaToSocialPostResponse
    • TriggerPipelineResponse
    • ScheduleSeriesResponse
    • ChatMessageResponse
    • GenerateIdeasResponse
    • PageInfo
    • Error
    • MutationError
    • AddKeywordResult
    • LocalError
    • LocalChatSession
    • LocalChatMessage
    • ChatSession
    • ChatMessage
    • ActionChip
  1. Webhooks

Synup Webhooks

Synup can notify your systems in near-real-time when things happen in your account — a listing gets connected, a review campaign is sent, a social post publishes, an AI post idea is generated, and more. When an event occurs, Synup sends an HTTP POST with a JSON body to a URL you configure. Every delivery is cryptographically signed so you can verify it genuinely came from Synup.
This guide covers how to set webhooks up on your side, how signing and endpoint verification work (and why), and the shape of every delivery. The exact payload of each event is documented under the Webhooks section.

Quick start#

1.
Stand up an HTTPS endpoint on your server that accepts POST requests (publicly reachable, valid TLS certificate).
2.
In Synup, go to Settings → Notifications → Configure Webhooks and set your Webhooks URL.
3.
Click Generate to create your Signing secret. Copy it and store it securely on your server — you'll use it to (a) verify incoming signatures and (b) answer the verification challenge.
4.
Implement two things in your endpoint: a signature check on every request, and a challenge response for the one-time verification handshake.
5.
Click Verify endpoint in Synup. Synup sends a signed challenge; your endpoint proves it holds the secret. On success the status turns verified and deliveries begin.
6.
That's it — you'll receive every event for the account. There is no per-event subscription: if webhooks are enabled and your endpoint is verified, all events deliver.
Delivery is gated on four things: the webhooks feature is enabled on your account, a Webhooks URL is set, a signing secret has been generated, and your endpoint has passed verification. If any is missing, events are not delivered.

Configuring your endpoint#

Your Webhooks URL must be:
HTTPS — plain HTTP is rejected.
Publicly resolvable — the host must resolve to a public IP. Internal/private addresses (loopback, RFC-1918, link-local, cloud metadata IPs, etc.) are refused.
Fast — respond within 10 seconds. Do the minimum synchronously (verify the signature, enqueue the payload) and process asynchronously. A slow endpoint is treated as a failed delivery.
Idempotent-friendly — you may occasionally receive the same event more than once. De-duplicate on the IDs inside data (they are stable).
You configure a single Webhooks URL per account; all event types are delivered to it.

The signing secret#

A per-account secret string you generate in Settings → Notifications. It is the shared key between Synup and your server. Because your endpoint is a public URL, the signing secret lets you prove a request actually came from Synup and was not tampered with in transit. The secret itself is never transmitted — every delivery instead carries an HMAC computed with it.
Every webhook request includes this header:
X-Synup-Signature: sha256=<base64( HMAC-SHA256(secret, raw_request_body) )>
To verify, on your side:
1.
Read the raw request body bytes exactly as received — do not re-serialize the parsed JSON (key order / whitespace differences break the HMAC).
2.
Compute HMAC-SHA256(your_secret, raw_body), Base64-encode it, and prefix with sha256=.
3.
Compare against the X-Synup-Signature header using a constant-time comparison.
4.
If they don't match, reject the request (return 401) and do not process it.
Rotating the secret. You can Regenerate the secret at any time. When you do, the old secret immediately stops validating and your endpoint's verified status is reset — update the secret on your server and re-verify before deliveries resume. (Changing the Webhooks URL also resets verification.)

Endpoint verification#

A one-time (repeatable) challenge–response handshake, triggered by the Verify endpoint button, that confirms your endpoint is reachable and actually holds the signing secret — before Synup starts sending real events. Verification is the final gate: deliveries stay off until it passes.
When you click Verify endpoint, Synup sends a signed POST with body:
{ "event": "endpoint.verification", "nonce": "<random hex string>", "timestamp": "<ISO-8601 UTC>" }
Your endpoint must recognize the special event endpoint.verification, compute HMAC-SHA256(secret, nonce) as a lowercase hex string, and reply HTTP 200 with that hex string as the body (a quoted/JSON-wrapped hex string is also accepted). Synup compares your reply to its own computation; on a match the endpoint is marked verified and deliveries turn on.
Verification is automatically reset to unverified when you change the Webhooks URL or regenerate the secret, or when a verification attempt fails (including when a previously-working endpoint later stops resolving or responding). Deliveries pause until you click Verify endpoint again.

Delivery mechanics — the payload envelope#

Every event (except the verification challenge) is delivered with the same top-level shape:
{
  "event": "connection.location_connected",
  "timestamp": "2026-07-15T14:32:10Z",
  "account_id": 11073,
  "location_id": "279381",
  "data": { }
}
FieldTypeNotes
eventstringThe dotted event name (e.g. campaign.sent).
timestampISO-8601 stringWhen the event was emitted (UTC).
account_idintegerThe Synup account the event belongs to.
location_idstring | nullNumeric string for location-scoped events; null for brand-scoped events (social posts, social connections, social ideas). For brand-scoped events the brand is identified by social_profile_id inside data.
dataobjectEvent-specific fields — documented per event under Webhooks.
agency_account_idintegerOnly present when the account is managed by a parent agency account.
scopestringOnly present for AI Post Idea events — "local" or "social".
Synup records each delivery attempt (attempt count, last attempt time, HTTP response code). Return a 2xx to acknowledge receipt; any non-2xx (or a timeout) is treated as a failed attempt. Optional fields are omitted from data when empty rather than sent as null — always code defensively and treat missing optional keys and null the same way.

Code samples#

Node.js (Express) — capture the raw body so the HMAC matches exactly:
Python (Flask):

Operational notes & FAQ#

One URL, all events. There is no per-event subscription. If webhooks are enabled and your endpoint is verified, you receive every event type.
Always verify the signature. Treat any request that fails signature verification as hostile — return 401 and ignore it.
Use the raw body for the HMAC. Re-serializing parsed JSON changes bytes and breaks verification.
Acknowledge fast (2xx), process later. You have ~10 seconds. Enqueue and return; do slow work off the request path.
Expect occasional duplicates. De-duplicate on the stable IDs inside data.
Ordering is not guaranteed. Don't assume events arrive in the exact order they occurred.
Rotating the secret or changing the URL resets verification — update your server and click Verify endpoint again to resume deliveries.
location_id is null for brand-scoped events (social posts, social connections, social ideas). Use social_profile_id inside data to identify the brand.
agency_account_id appears only when the account is managed by a parent agency.
Modified at 2026-07-15 18:06:40
Previous
Update idea
Next
Listing connected
Built with