---
updatedAt: 2026-08-06T19:51:59.000Z
agentTools:
  projectIndex: https://apidocs.zigpoll.com/llms.txt
---

# Register a signed webhook on a survey

Deliver a survey's responses to an https endpoint. Every delivery carries an HMAC `X-Zigpoll-Signature` header formatted `t=<unix ms>,v1=<hex>`, where v1 is HMAC-SHA256 over `<t>.<raw request body>`. Delivery is at-least-once and retried on failure, so dedupe on `X-Zigpoll-Delivery-Id`.

Returns the account's signing secret ONCE, in this response. No other call returns it — store it when you create the webhook.

Endpoints must be public https URLs; localhost, internal hosts and IP literals are rejected. Maximum 20 per survey. Requires admin access.


# OpenAPI definition

```json
{
  "openapi": "3.0.3",
  "info": {
    "title": "Zigpoll API",
    "version": "1.0.0",
    "description": "API for interacting with your Zigpoll surveys and responses.\n\nCounter fields use distinct units. `surveyResponseCount` holds **responses** -- one is counted each time a participant takes a survey, however many questions they answer. This is the unit plan limits apply to (`plan.submissionLimit`), and on an account it resets on the 1st of each month; `totalSurveyResponseCount` is the lifetime figure. `submissionCount` holds **answers** -- one is counted each time a participant answers one question, so a 5 question survey can produce up to 5 per response. `responseCount` holds the count of **write-ins** specifically -- the free-text answers participants typed. On a poll, `emailCount` holds email addresses **collected** by the survey and `outboundEmailCount` holds survey emails **sent** for it (automatic sends, campaigns and test sends, lifetime)."
  },
  "servers": [
    {
      "url": "https://v1.zigpoll.com",
      "description": "Production server for v1 API"
    }
  ],
  "components": {
    "securitySchemes": {
      "ApiKeyAuth": {
        "type": "apiKey",
        "in": "header",
        "name": "Authorization"
      }
    }
  },
  "security": [
    {
      "ApiKeyAuth": []
    }
  ],
  "paths": {
    "/webhooks": {
      "post": {
        "operationId": "createWebhook",
        "summary": "Register a signed webhook on a survey",
        "description": "Deliver a survey's responses to an https endpoint. Every delivery carries an HMAC `X-Zigpoll-Signature` header formatted `t=<unix ms>,v1=<hex>`, where v1 is HMAC-SHA256 over `<t>.<raw request body>`. Delivery is at-least-once and retried on failure, so dedupe on `X-Zigpoll-Delivery-Id`.\n\nReturns the account's signing secret ONCE, in this response. No other call returns it — store it when you create the webhook.\n\nEndpoints must be public https URLs; localhost, internal hosts and IP literals are rejected. Maximum 20 per survey. Requires admin access.\n",
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "pollId",
                  "endpoint"
                ],
                "properties": {
                  "pollId": {
                    "type": "string",
                    "description": "The ID of the poll whose responses to deliver."
                  },
                  "endpoint": {
                    "type": "string",
                    "description": "The https URL to POST each delivery to."
                  },
                  "notificationRules": {
                    "type": "string",
                    "enum": [
                      "always",
                      "strict"
                    ],
                    "default": "always",
                    "description": "`always` delivers on every submission, including from respondents who abandon the survey partway. `strict` delivers only once a respondent finishes."
                  }
                }
              },
              "example": {
                "pollId": "6789abcdef012345",
                "endpoint": "https://example.com/hooks/zigpoll",
                "notificationRules": "always"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The created webhook, including the signing secret (shown only here)",
            "content": {
              "application/json": {
                "example": {
                  "data": {
                    "key": "59f76bf7-81ff-4774-a0e2-4730c544a91c",
                    "pollId": "6789abcdef012345",
                    "endpoint": "https://example.com/hooks/zigpoll",
                    "notificationRules": "always",
                    "signingSecret": "0000000000000000000000000000000000000000000000000000000000000000"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Your role does not permit this action, or the account lacks API access"
          },
          "404": {
            "description": "Poll not found or you do not own the account it belongs to"
          },
          "422": {
            "description": "Validation error (non-https endpoint, non-public host, or the 20-per-survey cap)",
            "content": {
              "application/json": {
                "example": {
                  "error": "Webhook endpoints must use https://."
                }
              }
            }
          }
        }
      }
    }
  }
}
```