1729 lines
26 KiB
Markdown
1729 lines
26 KiB
Markdown
# X/Twitter Marketing Service - API Documentation
|
|
|
|
## Table of Contents
|
|
|
|
1. [API Overview](#api-overview)
|
|
2. [Authentication](#authentication)
|
|
3. [Account Management](#account-management)
|
|
4. [Contact Management](#contact-management)
|
|
5. [Conversation Management](#conversation-management)
|
|
6. [Template Management](#template-management)
|
|
7. [Campaign Management](#campaign-management)
|
|
8. [Segment Management](#segment-management)
|
|
9. [Automation Flows](#automation-flows)
|
|
10. [AI Chatbot](#ai-chatbot)
|
|
11. [Analytics](#analytics)
|
|
12. [Webhooks](#webhooks)
|
|
13. [Error Handling](#error-handling)
|
|
|
|
---
|
|
|
|
## API Overview
|
|
|
|
### Base URL
|
|
|
|
```
|
|
Development: http://localhost:5000/api/v1/mkt-x
|
|
Production: https://api.goodgo.com/api/v1/mkt-x
|
|
```
|
|
|
|
### Versioning
|
|
|
|
API versioning is handled through the URL path (`/api/v1/`).
|
|
|
|
### Request Format
|
|
|
|
All requests with body should use:
|
|
```
|
|
Content-Type: application/json
|
|
```
|
|
|
|
### Response Format
|
|
|
|
All responses follow this structure:
|
|
|
|
**Success Response**
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": { ... },
|
|
"pagination": {
|
|
"page": 1,
|
|
"limit": 20,
|
|
"total": 100,
|
|
"totalPages": 5
|
|
}
|
|
}
|
|
```
|
|
|
|
**Error Response**
|
|
```json
|
|
{
|
|
"success": false,
|
|
"error": "Error message description"
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Authentication
|
|
|
|
### JWT Bearer Token
|
|
|
|
All API endpoints (except webhooks) require authentication via JWT bearer token.
|
|
|
|
**Request Header**
|
|
```
|
|
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
|
|
```
|
|
|
|
### Obtaining Token
|
|
|
|
Tokens are obtained from the IAM service:
|
|
|
|
```bash
|
|
POST /api/v1/auth/login
|
|
Content-Type: application/json
|
|
|
|
{
|
|
"email": "user@example.com",
|
|
"password": "password"
|
|
}
|
|
```
|
|
|
|
**Response**
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"accessToken": "eyJhbGci...",
|
|
"refreshToken": "refresh...",
|
|
"expiresIn": 3600
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Account Management
|
|
|
|
### Connect Twitter Account
|
|
|
|
Connect a Twitter account using OAuth 1.0a credentials.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /accounts
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"oauthToken": "oauth_token_from_twitter",
|
|
"oauthTokenSecret": "oauth_token_secret_from_twitter"
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "550e8400-e29b-41d4-a716-446655440000",
|
|
"merchantId": "merchant-uuid",
|
|
"twitterUserId": "123456789",
|
|
"username": "goodgo_shop",
|
|
"displayName": "GoodGo Official",
|
|
"status": "active",
|
|
"connectedAt": "2026-01-18T10:00:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Error Codes**
|
|
- `400` - Invalid OAuth credentials
|
|
- `401` - Unauthorized
|
|
- `409` - Account already connected
|
|
|
|
---
|
|
|
|
### List Connected Accounts
|
|
|
|
Get all Twitter accounts connected by the merchant.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /accounts
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `status` (optional) - Filter by status: `active`, `inactive`, `error`
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": [
|
|
{
|
|
"id": "uuid",
|
|
"merchantId": "uuid",
|
|
"twitterUserId": "123456789",
|
|
"username": "goodgo_shop",
|
|
"displayName": "GoodGo Official",
|
|
"status": "active",
|
|
"connectedAt": "2026-01-18T10:00:00Z"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Get Account Details
|
|
|
|
Get detailed information about a specific Twitter account.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /accounts/{accountId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"merchantId": "uuid",
|
|
"twitterUserId": "123456789",
|
|
"username": "goodgo_shop",
|
|
"displayName": "GoodGo Official",
|
|
"profileImageUrl": "https://pbs.twimg.com/profile_images/...",
|
|
"status": "active",
|
|
"webhookId": "webhook-id",
|
|
"connectedAt": "2026-01-18T10:00:00Z",
|
|
"statistics": {
|
|
"totalContacts": 1234,
|
|
"totalConversations": 567,
|
|
"messagesThisMonth": 890
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
**Error Codes**
|
|
- `404` - Account not found
|
|
|
|
---
|
|
|
|
### Disconnect Account
|
|
|
|
Disconnect a Twitter account and revoke OAuth tokens.
|
|
|
|
**Endpoint**
|
|
```
|
|
DELETE /accounts/{accountId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": null
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Update Account Settings
|
|
|
|
Update account configuration settings.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /accounts/{accountId}
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"autoReplyEnabled": true,
|
|
"businessHours": {
|
|
"enabled": true,
|
|
"timezone": "Asia/Ho_Chi_Minh",
|
|
"schedule": {
|
|
"monday": { "start": "09:00", "end": "18:00" },
|
|
"tuesday": { "start": "09:00", "end": "18:00" }
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
## Contact Management
|
|
|
|
### List Contacts
|
|
|
|
Get paginated list of contacts with filtering.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /contacts
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `accountId` (optional) - Filter by Twitter account
|
|
- `tags` (optional) - Comma-separated tags: `vip,customer`
|
|
- `search` (optional) - Search in username/display name
|
|
- `skip` (optional, default: 0) - Pagination offset
|
|
- `take` (optional, default: 20, max: 100) - Items per page
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": [
|
|
{
|
|
"id": "uuid",
|
|
"accountId": "uuid",
|
|
"twitterUserId": "987654321",
|
|
"username": "customer_john",
|
|
"displayName": "John Doe",
|
|
"profileImageUrl": "https://...",
|
|
"tags": ["vip", "customer"],
|
|
"attributes": {
|
|
"purchaseCount": 5,
|
|
"totalSpent": 1250000,
|
|
"lastPurchaseDate": "2026-01-15"
|
|
},
|
|
"conversationCount": 3,
|
|
"firstInteractionAt": "2025-12-01T10:00:00Z",
|
|
"lastInteractionAt": "2026-01-18T09:30:00Z"
|
|
}
|
|
],
|
|
"pagination": {
|
|
"page": 1,
|
|
"limit": 20,
|
|
"total": 1234,
|
|
"totalPages": 62
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Get Contact Details
|
|
|
|
Get detailed information about a specific contact.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /contacts/{contactId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"accountId": "uuid",
|
|
"twitterUserId": "987654321",
|
|
"username": "customer_john",
|
|
"displayName": "John Doe",
|
|
"profileImageUrl": "https://...",
|
|
"tags": ["vip", "customer"],
|
|
"attributes": {
|
|
"purchaseCount": 5,
|
|
"totalSpent": 1250000,
|
|
"lastPurchaseDate": "2026-01-15",
|
|
"preferredLanguage": "vi"
|
|
},
|
|
"source": "inbound_message",
|
|
"conversationCount": 3,
|
|
"firstInteractionAt": "2025-12-01T10:00:00Z",
|
|
"lastInteractionAt": "2026-01-18T09:30:00Z",
|
|
"engagement": {
|
|
"messagesSent": 15,
|
|
"messagesReceived": 18,
|
|
"averageResponseTime": "5m 30s"
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Update Contact
|
|
|
|
Update contact information.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /contacts/{contactId}
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"displayName": "John Doe (VIP)",
|
|
"attributes": {
|
|
"preferredLanguage": "en",
|
|
"notes": "Premium customer"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Add Tags to Contact
|
|
|
|
Add one or more tags to a contact.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /contacts/{contactId}/tags
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"tags": ["vip", "premium"]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Remove Tag from Contact
|
|
|
|
Remove a specific tag from a contact.
|
|
|
|
**Endpoint**
|
|
```
|
|
DELETE /contacts/{contactId}/tags/{tagName}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Update Contact Attributes
|
|
|
|
Bulk update custom attributes for a contact.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /contacts/{contactId}/attributes
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"attributes": {
|
|
"purchaseCount": 6,
|
|
"totalSpent": 1500000,
|
|
"lastPurchaseDate": "2026-01-18",
|
|
"membershipTier": "gold"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Contact Conversations
|
|
|
|
Get all conversations for a specific contact.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /contacts/{contactId}/conversations
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `status` (optional) - Filter by status: `open`, `closed`
|
|
- `skip` (optional) - Pagination offset
|
|
- `take` (optional) - Items per page
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": [
|
|
{
|
|
"id": "uuid",
|
|
"contactId": "uuid",
|
|
"status": "open",
|
|
"messageCount": 5,
|
|
"startedAt": "2026-01-18T09:00:00Z",
|
|
"lastMessageAt": "2026-01-18T09:30:00Z"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Delete Contact
|
|
|
|
Delete a contact and all associated data (GDPR compliance).
|
|
|
|
**Endpoint**
|
|
```
|
|
DELETE /contacts/{contactId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
## Conversation Management
|
|
|
|
### List Conversations
|
|
|
|
Get paginated list of conversations.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /conversations
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `accountId` (optional) - Filter by account
|
|
- `status` (optional) - Filter by status: `open`, `closed`
|
|
- `assignedTo` (optional) - Filter by assigned user ID
|
|
- `skip` (optional) - Pagination offset
|
|
- `take` (optional) - Items per page
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": [
|
|
{
|
|
"id": "uuid",
|
|
"contactId": "uuid",
|
|
"accountId": "uuid",
|
|
"status": "open",
|
|
"channel": "direct_message",
|
|
"assignedToUserId": "uuid",
|
|
"messageCount": 12,
|
|
"startedAt": "2026-01-18T09:00:00Z",
|
|
"lastMessageAt": "2026-01-18T10:15:00Z",
|
|
"contact": {
|
|
"username": "customer_john",
|
|
"displayName": "John Doe"
|
|
}
|
|
}
|
|
],
|
|
"pagination": { ... }
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Get Conversation with Messages
|
|
|
|
Get conversation details including all messages.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /conversations/{conversationId}
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `includeMessages` (optional, default: true) - Include message history
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"contactId": "uuid",
|
|
"accountId": "uuid",
|
|
"status": "open",
|
|
"channel": "direct_message",
|
|
"assignedToUserId": "uuid",
|
|
"startedAt": "2026-01-18T09:00:00Z",
|
|
"messages": [
|
|
{
|
|
"id": "uuid",
|
|
"conversationId": "uuid",
|
|
"direction": "inbound",
|
|
"type": "text",
|
|
"content": "Hello, I have a question about my order",
|
|
"attachments": [],
|
|
"isFromBot": false,
|
|
"sentAt": "2026-01-18T09:00:00Z"
|
|
},
|
|
{
|
|
"id": "uuid",
|
|
"conversationId": "uuid",
|
|
"direction": "outbound",
|
|
"type": "text",
|
|
"content": "Hi! I'd be happy to help. What's your order number?",
|
|
"attachments": [],
|
|
"isFromBot": false,
|
|
"sentAt": "2026-01-18T09:02:00Z"
|
|
}
|
|
]
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Send Message
|
|
|
|
Send a message in a conversation.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /conversations/{conversationId}/messages
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"content": "Your order #12345 has been shipped!",
|
|
"type": "text",
|
|
"attachments": [
|
|
{
|
|
"type": "image",
|
|
"url": "https://example.com/tracking.png"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"conversationId": "uuid",
|
|
"twitterMessageId": "123456789",
|
|
"direction": "outbound",
|
|
"type": "text",
|
|
"content": "Your order #12345 has been shipped!",
|
|
"sentAt": "2026-01-18T10:30:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Error Codes**
|
|
- `400` - Message content exceeds Twitter limits (10,000 chars)
|
|
- `429` - Rate limit exceeded
|
|
|
|
---
|
|
|
|
### Close Conversation
|
|
|
|
Close an active conversation.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /conversations/{conversationId}/close
|
|
```
|
|
|
|
**Request Body** (optional)
|
|
```json
|
|
{
|
|
"reason": "resolved"
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Assign Conversation
|
|
|
|
Assign conversation to a specific user/agent.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /conversations/{conversationId}/assign
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"userId": "user-uuid"
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
## Template Management
|
|
|
|
### Create Template
|
|
|
|
Create a new message template.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /templates
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "Welcome Message",
|
|
"type": "text",
|
|
"content": "Hi {{name}}, welcome to {{shop_name}}! Use code {{discount_code}} for 10% off your first order.",
|
|
"variables": ["name", "shop_name", "discount_code"]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"merchantId": "uuid",
|
|
"name": "Welcome Message",
|
|
"type": "text",
|
|
"content": "Hi {{name}}, welcome to...",
|
|
"variables": ["name", "shop_name", "discount_code"],
|
|
"createdAt": "2026-01-18T10:00:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### List Templates
|
|
|
|
Get all templates for the merchant.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /templates
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `type` (optional) - Filter by type: `text`, `quick_reply`, `card`
|
|
- `search` (optional) - Search in template name
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Template
|
|
|
|
Get template details.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /templates/{templateId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Update Template
|
|
|
|
Update existing template.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /templates/{templateId}
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "Updated Welcome Message",
|
|
"content": "Hello {{name}}!..."
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Delete Template
|
|
|
|
Delete a template.
|
|
|
|
**Endpoint**
|
|
```
|
|
DELETE /templates/{templateId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
**Error Codes**
|
|
- `409` - Template is being used by active campaigns
|
|
|
|
---
|
|
|
|
### Preview Template
|
|
|
|
Preview rendered template with sample data.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /templates/{templateId}/preview
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"variables": {
|
|
"name": "John",
|
|
"shop_name": "GoodGo Shop",
|
|
"discount_code": "WELCOME10"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"rendered": "Hi John, welcome to GoodGo Shop! Use code WELCOME10 for 10% off your first order."
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Campaign Management
|
|
|
|
### Create Campaign
|
|
|
|
Create a new marketing campaign.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /campaigns
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "January Promotion",
|
|
"type": "promotional",
|
|
"templateId": "template-uuid",
|
|
"segmentIds": ["segment-uuid-1", "segment-uuid-2"],
|
|
"schedule": {
|
|
"startAt": "2026-01-20T10:00:00Z",
|
|
"endAt": null,
|
|
"recurrence": null
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"merchantId": "uuid",
|
|
"name": "January Promotion",
|
|
"type": "promotional",
|
|
"status": "draft",
|
|
"templateId": "uuid",
|
|
"segmentIds": ["uuid"],
|
|
"schedule": { ... },
|
|
"metrics": {
|
|
"totalSent": 0,
|
|
"delivered": 0,
|
|
"opened": 0,
|
|
"clicked": 0,
|
|
"replied": 0,
|
|
"failed": 0
|
|
},
|
|
"createdAt": "2026-01-18T10:00:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### List Campaigns
|
|
|
|
Get all campaigns.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /campaigns
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `status` (optional) - Filter: `draft`, `scheduled`, `running`, `paused`, `completed`
|
|
- `type` (optional) - Filter: `promotional`, `transactional`, `engagement`
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Campaign
|
|
|
|
Get campaign details.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /campaigns/{campaignId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Update Campaign
|
|
|
|
Update campaign (only for draft/scheduled campaigns).
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /campaigns/{campaignId}
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "Updated Campaign Name",
|
|
"schedule": {
|
|
"startAt": "2026-01-21T10:00:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
**Error Codes**
|
|
- `400` - Cannot update running/completed campaigns
|
|
|
|
---
|
|
|
|
### Start Campaign
|
|
|
|
Start campaign execution.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /campaigns/{campaignId}/start
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
**Error Codes**
|
|
- `400` - Campaign has no segments or invalid template
|
|
|
|
---
|
|
|
|
### Pause Campaign
|
|
|
|
Pause a running campaign.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /campaigns/{campaignId}/pause
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Resume Campaign
|
|
|
|
Resume a paused campaign.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /campaigns/{campaignId}/resume
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Campaign Metrics
|
|
|
|
Get detailed campaign performance metrics.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /campaigns/{campaignId}/metrics
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"totalSent": 1500,
|
|
"delivered": 1450,
|
|
"opened": 800,
|
|
"clicked": 250,
|
|
"replied": 45,
|
|
"failed": 50,
|
|
"openRate": 0.55,
|
|
"clickRate": 0.17,
|
|
"replyRate": 0.03,
|
|
"deliveryRate": 0.97,
|
|
"timeline": [
|
|
{
|
|
"timestamp": "2026-01-20T10:00:00Z",
|
|
"sent": 500,
|
|
"delivered": 485
|
|
}
|
|
]
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Send Test Campaign
|
|
|
|
Send test message to specific contacts.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /campaigns/{campaignId}/test
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"contactIds": ["contact-uuid-1", "contact-uuid-2"],
|
|
"variables": {
|
|
"discount_code": "TEST10"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
## Segment Management
|
|
|
|
### Create Segment
|
|
|
|
Create a customer segment with conditions.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /segments
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "VIP Customers",
|
|
"conditions": [
|
|
{
|
|
"field": "tags",
|
|
"operator": "contains",
|
|
"value": "vip"
|
|
},
|
|
{
|
|
"field": "attributes.purchaseCount",
|
|
"operator": "greaterThan",
|
|
"value": 5
|
|
},
|
|
{
|
|
"field": "lastInteractionAt",
|
|
"operator": "after",
|
|
"value": "2026-01-01T00:00:00Z"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"id": "uuid",
|
|
"merchantId": "uuid",
|
|
"name": "VIP Customers",
|
|
"conditions": [ ... ],
|
|
"contactCount": 0,
|
|
"createdAt": "2026-01-18T10:00:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### List Segments
|
|
|
|
Get all segments.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /segments
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Segment
|
|
|
|
Get segment details.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /segments/{segmentId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Update Segment
|
|
|
|
Update segment conditions.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /segments/{segmentId}
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "Updated VIP Customers",
|
|
"conditions": [ ... ]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Delete Segment
|
|
|
|
Delete a segment.
|
|
|
|
**Endpoint**
|
|
```
|
|
DELETE /segments/{segmentId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
**Error Codes**
|
|
- `409` - Segment is being used by active campaigns
|
|
|
|
---
|
|
|
|
### Preview Segment Contacts
|
|
|
|
Preview contacts that match segment conditions.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /segments/{segmentId}/preview
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `limit` (optional, default: 10, max: 50) - Number of contacts to preview
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"totalMatches": 234,
|
|
"preview": [
|
|
{
|
|
"id": "uuid",
|
|
"username": "customer_john",
|
|
"displayName": "John Doe",
|
|
"tags": ["vip"],
|
|
"attributes": {
|
|
"purchaseCount": 8
|
|
}
|
|
}
|
|
]
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Automation Flows
|
|
|
|
### Create Automation Flow
|
|
|
|
Create a new automation workflow.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /automation/flows
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "Welcome Flow",
|
|
"trigger": {
|
|
"type": "new_follower",
|
|
"config": {}
|
|
},
|
|
"nodes": [
|
|
{
|
|
"id": "node-1",
|
|
"type": "send_message",
|
|
"config": {
|
|
"templateId": "template-uuid",
|
|
"delay": 0
|
|
}
|
|
},
|
|
{
|
|
"id": "node-2",
|
|
"type": "wait",
|
|
"config": {
|
|
"duration": 86400
|
|
}
|
|
},
|
|
{
|
|
"id": "node-3",
|
|
"type": "send_message",
|
|
"config": {
|
|
"templateId": "template-uuid-2",
|
|
"delay": 0
|
|
}
|
|
}
|
|
],
|
|
"connections": [
|
|
{
|
|
"fromNodeId": "node-1",
|
|
"toNodeId": "node-2"
|
|
},
|
|
{
|
|
"fromNodeId": "node-2",
|
|
"toNodeId": "node-3"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### List Automation Flows
|
|
|
|
Get all automation flows.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /automation/flows
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `status` (optional) - Filter: `active`, `inactive`, `draft`
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Automation Flow
|
|
|
|
Get flow details.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /automation/flows/{flowId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Update Automation Flow
|
|
|
|
Update flow configuration.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /automation/flows/{flowId}
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "Updated Welcome Flow",
|
|
"nodes": [ ... ],
|
|
"connections": [ ... ]
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
**Error Codes**
|
|
- `400` - Cannot update active flows (deactivate first)
|
|
|
|
---
|
|
|
|
### Activate Flow
|
|
|
|
Activate an automation flow.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /automation/flows/{flowId}/activate
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Deactivate Flow
|
|
|
|
Deactivate a running flow.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /automation/flows/{flowId}/deactivate
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Delete Flow
|
|
|
|
Delete an automation flow.
|
|
|
|
**Endpoint**
|
|
```
|
|
DELETE /automation/flows/{flowId}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Flow Executions
|
|
|
|
Get execution history for a flow.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /automation/flows/{flowId}/executions
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `status` (optional) - Filter: `running`, `completed`, `failed`
|
|
- `skip`, `take` - Pagination
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": [
|
|
{
|
|
"id": "uuid",
|
|
"flowId": "uuid",
|
|
"contactId": "uuid",
|
|
"status": "completed",
|
|
"currentNodeId": null,
|
|
"startedAt": "2026-01-18T09:00:00Z",
|
|
"completedAt": "2026-01-19T09:00:00Z"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## AI Chatbot
|
|
|
|
### Send Message to AI
|
|
|
|
Send a message to AI chatbot for processing.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /ai/conversations/{conversationId}/message
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"message": "What's the status of my order #12345?"
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"intent": "order_status_query",
|
|
"confidence": 0.95,
|
|
"response": "Let me check that for you. Order #12345 was shipped on January 15 and is expected to arrive on January 20.",
|
|
"slots": {
|
|
"orderId": "12345"
|
|
},
|
|
"requiresEscalation": false
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Get Conversation Context
|
|
|
|
Get AI conversation context.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /ai/conversations/{conversationId}/context
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"sessionId": "uuid",
|
|
"context": [
|
|
{
|
|
"role": "user",
|
|
"content": "What's the status of my order?"
|
|
},
|
|
{
|
|
"role": "assistant",
|
|
"content": "I'd be happy to help! What's your order number?"
|
|
}
|
|
],
|
|
"currentIntent": "order_status_query",
|
|
"slots": {
|
|
"orderId": "12345"
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Escalate to Human
|
|
|
|
Escalate AI conversation to human agent.
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /ai/conversations/{conversationId}/escalate
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"reason": "complex_query"
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Update AI Settings
|
|
|
|
Update AI chatbot settings for the merchant.
|
|
|
|
**Endpoint**
|
|
```
|
|
PUT /ai/settings
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"enabled": true,
|
|
"model": "gpt-4",
|
|
"temperature": 0.7,
|
|
"maxTokens": 500,
|
|
"autoEscalationThreshold": 0.6,
|
|
"systemPrompt": "You are a helpful customer service assistant for GoodGo Shop..."
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
## Analytics
|
|
|
|
### Get Overview Analytics
|
|
|
|
Get dashboard overview analytics.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /analytics/overview
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `startDate` (required) - ISO 8601 date
|
|
- `endDate` (required) - ISO 8601 date
|
|
- `accountId` (optional) - Filter by account
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"success": true,
|
|
"data": {
|
|
"period": {
|
|
"startDate": "2026-01-01T00:00:00Z",
|
|
"endDate": "2026-01-18T23:59:59Z"
|
|
},
|
|
"contacts": {
|
|
"total": 1234,
|
|
"new": 156,
|
|
"active": 456
|
|
},
|
|
"conversations": {
|
|
"total": 567,
|
|
"open": 45,
|
|
"closed": 522,
|
|
"averageResponseTime": "5m 30s"
|
|
},
|
|
"campaigns": {
|
|
"active": 3,
|
|
"completed": 12,
|
|
"totalMessagesSent": 15000
|
|
},
|
|
"automation": {
|
|
"activeFlows": 5,
|
|
"totalExecutions": 890
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Get Contact Analytics
|
|
|
|
Get contact-related analytics.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /analytics/contacts
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `startDate`, `endDate` - Date range
|
|
- `groupBy` (optional) - Group by: `day`, `week`, `month`
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Conversation Analytics
|
|
|
|
Get conversation analytics.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /analytics/conversations
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Campaign Analytics
|
|
|
|
Get campaign performance analytics.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /analytics/campaigns
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `campaignId` (optional) - Specific campaign
|
|
- `startDate`, `endDate` - Date range
|
|
|
|
**Response** `200 OK`
|
|
|
|
---
|
|
|
|
### Get Automation Analytics
|
|
|
|
Get automation flow analytics.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /analytics/automation
|
|
```
|
|
|
|
**Response** `200 OK**
|
|
|
|
---
|
|
|
|
## Webhooks
|
|
|
|
### Receive Twitter Webhook Events
|
|
|
|
Endpoint for receiving Twitter webhook events (Account Activity API).
|
|
|
|
**Endpoint**
|
|
```
|
|
POST /webhooks/twitter
|
|
```
|
|
|
|
**Headers**
|
|
```
|
|
X-Twitter-Webhooks-Signature: sha256=...
|
|
```
|
|
|
|
**Request Body** (example: Direct Message Event)
|
|
```json
|
|
{
|
|
"direct_message_events": [
|
|
{
|
|
"id": "123456789",
|
|
"created_timestamp": "1642000000000",
|
|
"message_create": {
|
|
"sender_id": "987654321",
|
|
"target": {
|
|
"recipient_id": "123456789"
|
|
},
|
|
"message_data": {
|
|
"text": "Hello!",
|
|
"entities": {}
|
|
}
|
|
}
|
|
}
|
|
],
|
|
"users": {
|
|
"987654321": {
|
|
"id": "987654321",
|
|
"screen_name": "customer_john",
|
|
"name": "John Doe"
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
**Response** `200 OK`
|
|
|
|
**Note**: This endpoint validates the Twitter signature for security.
|
|
|
|
---
|
|
|
|
### Twitter CRC Verification
|
|
|
|
Twitter Challenge-Response Check for webhook verification.
|
|
|
|
**Endpoint**
|
|
```
|
|
GET /webhooks/verify
|
|
```
|
|
|
|
**Query Parameters**
|
|
- `crc_token` - Token from Twitter
|
|
|
|
**Response** `200 OK`
|
|
```json
|
|
{
|
|
"response_token": "sha256=base64_encoded_hmac"
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Error Handling
|
|
|
|
### HTTP Status Codes
|
|
|
|
| Code | Meaning | Description |
|
|
|------|---------|-------------|
|
|
| 200 | OK | Request successful |
|
|
| 201 | Created | Resource created |
|
|
| 400 | Bad Request | Invalid request parameters |
|
|
| 401 | Unauthorized | Missing or invalid auth token |
|
|
| 403 | Forbidden | Insufficient permissions |
|
|
| 404 | Not Found | Resource not found |
|
|
| 409 | Conflict | Resource already exists or conflict |
|
|
| 422 | Unprocessable Entity | Validation failed |
|
|
| 429 | Too Many Requests | Rate limit exceeded |
|
|
| 500 | Internal Server Error | Server error |
|
|
| 503 | Service Unavailable | Service temporarily unavailable |
|
|
|
|
### Error Response Format
|
|
|
|
```json
|
|
{
|
|
"success": false,
|
|
"error": "Detailed error message",
|
|
"code": "ERROR_CODE",
|
|
"details": {
|
|
"field": "templateId",
|
|
"reason": "Template not found"
|
|
}
|
|
}
|
|
```
|
|
|
|
### Common Error Codes
|
|
|
|
| Code | Description |
|
|
|------|-------------|
|
|
| `VALIDATION_ERROR` | Request validation failed |
|
|
| `UNAUTHORIZED` | Authentication required |
|
|
| `FORBIDDEN` | Insufficient permissions |
|
|
| `RESOURCE_NOT_FOUND` | Requested resource not found |
|
|
| `DUPLICATE_RESOURCE` | Resource already exists |
|
|
| `RATE_LIMIT_EXCEEDED` | Too many requests |
|
|
| `TWITTER_API_ERROR` | Twitter API error |
|
|
| `AI_SERVICE_ERROR` | AI service error |
|
|
|
|
### Rate Limiting
|
|
|
|
**Headers**
|
|
```
|
|
X-RateLimit-Limit: 100
|
|
X-RateLimit-Remaining: 95
|
|
X-RateLimit-Reset: 1642000000
|
|
```
|
|
|
|
**Limits**
|
|
- API calls: 100 requests/minute per merchant
|
|
- Campaigns: 10,000 messages/day per account
|
|
- Messages: 500 messages/24 hours per Twitter account (Twitter limit)
|
|
|
|
---
|
|
|
|
## Postman Collection
|
|
|
|
Download the complete Postman collection for testing:
|
|
```
|
|
https://api.goodgo.com/api/v1/mkt-x/postman-collection.json
|
|
```
|
|
|
|
---
|
|
|
|
## Support
|
|
|
|
For API support, contact: api-support@goodgo.com
|