{
  "x-docs-deprecation": "Note: The 'qualityScore' field is deprecated and will be removed in a future release. Please use 'demeritScore' instead.",
  "openapi": "3.0.0",
  "info": {
    "title": "Followup Generation API",
    "version": "1.0.0", 
    "description": "API for generating followup questions based on survey responses",
    "contact": {
      "name": "API Support",
      "email": "justin@getaftercare.com"
    },
    "license": {
      "name": "Apache 2.0",
      "url": "https://www.apache.org/licenses/LICENSE-2.0.html"
    }
  },
  "servers": [
    {
      "url": "https://surveys.getaftercare.com",
      "description": "Production server"
    },
    {
      "url": "https://staging.aftercareai.com", 
      "description": "Staging server"
    }
  ],
  "tags": [
    {
      "name": "Followups",
      "description": "Operations related to followup question generation"
    },
    {
      "name": "Data Quality",
      "description": "Operations related to response data quality evaluation"
    },
    {
      "name": "Coding",
      "description": "Operations related to coding survey responses"
    }
  ],
  "security": [
    {
      "ApiKeyAuth": []
    }
  ],
  "paths": {
    "/api/v1/followups": {
      "post": {
        "tags": ["Followups"],
        "summary": "Generate a followup question",
        "description": "Generates a contextual followup question based on a survey response",
        "operationId": "generateFollowup",
        "parameters": [
          {"$ref": "#/components/parameters/X-Request-Encoding"},
          {"$ref": "#/components/parameters/X-Response-Encoding"}
        ],
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
              "source": "const response = await api.followups.generate({\n  surveyName: 'Customer Satisfaction',\n  question: 'How likely are you to recommend our service?',\n  answer: 'Very likely, the customer service is excellent',\n  surveyIdentifiers: {\n    surveyIdentifier: 'CSAT-2024-Q1',\n    questionIdentifier: 'NPS-1'\n  }\n});"
          },
          {
            "lang": "Python",
            "source": "response = api.followups.generate(\n    survey_name='Customer Satisfaction',\n    question='How likely are you to recommend our service?',\n    answer='Very likely, the customer service is excellent',\n    surveyIdentifiers={\n        'survey_identifier': 'CSAT-2024-Q1',\n        'question_identifier': 'NPS-1'\n    }\n)"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/FollowupGenerationRequest"
              },
              "example": {
                "surveyName": "Customer Satisfaction",
                "surveyDescription": "Tracking customer satisfaction and loyalty for the XYZ Company",
                "question": "How likely are you to recommend our service?",
                "questionContext": "I want to understand specifically why a customer is convinced to recommend our service. If they are not recommending our service, I want to know why.",
                "answer": "Very likely, the customer service is excellent",
                "surveyIdentifiers": {
                  "surveyIdentifier": "CSAT-2024-Q1",
                  "questionIdentifier": "NPS-1"
                },
                "guidanceBehavior": "Verbose"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successfully generated followup question",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/FollowupGenerationResponse"
                },
                "example": {
                  "followupQuestion": "What specific aspects of our customer service impressed you the most?",
                  "responseEvaluation": {
                    "completeness": 75,
                    "relevance": 90
                  },
                  "threadId": "7a54b8da-f65d-4946-9c9a-f202e0cc29c8",
                  "responseIdentifier": "12345"
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid request parameters",
                  "details": {
                    "question": "Question is required"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "404": {
            "description": "Resource not found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "NOT_FOUND",
                  "message": "Requested resource not found"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          },
          "504": {
            "description": "Gateway timeout",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "GATEWAY_TIMEOUT",
                  "message": "The request timed out"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/data-quality": {
      "post": {
        "tags": ["Data Quality"],
        "summary": "Evaluate survey response quality",
        "description": "Evaluates the quality of survey responses for potential issues",
        "operationId": "evaluateDataQuality",
        "parameters": [
          {"$ref": "#/components/parameters/X-Request-Encoding"}
        ],
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
            "source": "const response = await api.quality.evaluate({\n  surveyName: 'Customer Satisfaction',\n  surveyEntries: [{\n    question: 'How satisfied are you?',\n    answer: 'I really love playing tennis with my friends on Fridays'\n  }]\n});"
          },
          {
            "lang": "Python",
            "source": "response = api.quality.evaluate(\n    survey_name='Customer Satisfaction',\n    survey_entries=[{\n        'question': 'How satisfied are you?',\n        'answer': 'I really love playing tennis with my friends on Fridays'\n    }]\n)"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/DataQualityRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successfully evaluated survey quality",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DataQualityResponse"
                },
                "example": {
                  "numIssues": 1,
                  "qualityScore": 30,
                  "demeritScore": 70,
                  "evaluations": [
                    {
                      "surveyEntry": {
                        "question": "How satisfied were you with our service?",
                        "answer": "I really love playing tennis with my friends on Fridays"
                      },
                      "numIssues": 1,
                      "qualityScore": 30,
                      "demeritScore": 70,
                      "qualityIssueChecks": [
                        {
                          "type": "Irrelevant",
                          "score": 10,
                          "isIssue": true
                        },
                        {
                          "type": "Nonsensical",
                          "score": 80,
                          "isIssue": true
                        },
                        {
                          "type": "Incomplete",
                          "score": 60,
                          "isIssue": false
                        },
                        {
                          "type": "Low Effort",
                          "score": 95,
                          "isIssue": true
                        },
                        {
                          "type": "LLM Generated",
                          "score": 80,
                          "isIssue": false
                        },
                        {
                          "type": "Self Duplicated",
                          "score": 30,
                          "isIssue": false
                        },
                        {
                          "type": "Shared Duplicate",
                          "score": 30,
                          "isIssue": false
                        }
                      ]
                    }
                  ],
                  "aftercareResponseIdentifier": 12345
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid request parameters",
                  "details": {
                    "question": "Question is required"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "404": {
            "description": "Resource not found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "NOT_FOUND",
                  "message": "Requested resource not found"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          },
          "504": {
            "description": "Gateway timeout",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "GATEWAY_TIMEOUT",
                  "message": "The request timed out"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/data-quality/batch": {
      "post": {
        "tags": ["Data Quality", "Batch"],
        "summary": "Batch evaluate survey response quality",
        "description": "Asynchronously evaluates the quality of multiple survey responses",
        "operationId": "evaluateDataQualityBatch",
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
            "source": "const response = await api.quality.evaluateBatch({\n  surveyName: 'Customer Satisfaction',\n  responses: [{\n    responseIdentifier: '54321',\n    surveyEntries: [{\n        question: 'How satisfied are you?',\n        answer: 'I really love playing tennis with my friends on Fridays'\n    }]\n  }],\n  callbackUrl: 'https://example.com/callback'\n});"
          },
          {
            "lang": "Python",
            "source": "response = api.quality.evaluateBatch(\n    survey_name='Customer Satisfaction',\n    responses=[{\n        responseIdentifier: '54321',\n        'surveyEntries': [{\n            'question': 'How satisfied are you?',\n            'answer': 'I really love playing tennis with my friends on Fridays'\n        }]\n    }],\n    callback_url='https://example.com/callback'\n)"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/DataQualityBatchRequest"
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Batch evaluation job accepted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DataQualityBatchResponse"
                },
                "example": {
                  "batchJobId": "123e4567-e89b-12d3-a456-426614174000",
                  "status": "queued",
                  "results": {
                    "items": [],
                    "nextCursor": null
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid request parameters",
                  "details": {
                    "question": "Question is required"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "404": {
            "description": "Resource not found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "NOT_FOUND",
                  "message": "Requested resource not found"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/data-quality/batch/{batchJobId}": {
      "get": {
        "tags": ["Data Quality", "Batch"],
        "summary": "Get batch job status",
        "description": "Retrieves the current status and results of a batch evaluation job",
        "operationId": "getBatchJobStatus",
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
            "source": "const response = await api.quality.getBatchJobStatus();"
          },
          {
            "lang": "Python",
            "source": "response = api.quality.getBatchJobStatus()"
          }
        ],
        "parameters": [
          {
            "name": "batchJobId",
            "in": "path",
            "required": true,
            "description": "ID of the batch job to check",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Batch job status retrieved successfully",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DataQualityBatchResponse"
                },
                "example": {
                  "batchJobId": "123e4567-e89b-12d3-a456-426614174000",
                  "status": "completed",
                  "results": {
                    "items": [],
                    "nextCursor": null
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid request parameters",
                  "details": {
                    "question": "Question is required"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "404": {
            "description": "Resource not found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "NOT_FOUND",
                  "message": "Requested resource not found"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/coding": {
      "post": {
        "tags": ["Coding"],
        "summary": "Create a batch coding job",
        "description": "Analyze survey responses and code them into hierarchical categories",
        "operationId": "createBatchCodingJob",
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
            "source": "const response = await api.coding.createBatchJob({\n  surveyIdentifier: 'CSAT-2024-Q1',\n  surveyName: 'Customer Satisfaction',\n  surveyDescription: 'Tracking customer satisfaction and loyalty',\n  surveyResponses: [{\n    questionIdentifier: 'Q1',\n    question: 'What did you like about our service?',\n    responseEntries: [{\n      responseIdentifier: '12345',\n      answer: 'The customer service representatives were very helpful.'\n    }]\n  }]\n});"
          },
          {
            "lang": "Python",
            "source": "response = api.coding.create_batch_job(\n    survey_identifier='CSAT-2024-Q1',\n    survey_name='Customer Satisfaction',\n    survey_description='Tracking customer satisfaction and loyalty',\n    survey_responses=[{\n        'question_identifier': 'Q1',\n        'question': 'What did you like about our service?',\n        'response_entries': [{\n            'response_identifier': '12345',\n            'answer': 'The customer service representatives were very helpful.'\n        }]\n    }]\n)"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchCodingRequest"
              },
              "example": {
                "surveyIdentifier": "CSAT-2024-Q1",
                "surveyName": "Customer Satisfaction",
                "surveyDescription": "Tracking customer satisfaction and loyalty for the XYZ Company",
                "surveyResponses": [
                  {
                    "questionIdentifier": "Q1",
                    "question": "What did you like about our service?",
                    "questionContext": "I want to understand what aspects of our customer experience are working well.",
                    "responseEntries": [
                      {
                        "responseIdentifier": "12345",
                        "answer": "The customer service representatives were very helpful and resolved my issue quickly."
                      },
                      {
                        "responseIdentifier": "12346",
                        "answer": "I liked the easy-to-use website and fast delivery."
                      }
                    ],
                    "codingOptions": {
                      "maxLevels": 3,
                      "maxCodesPerLevel": [8, 5, 3],
                      "minResponsesPerCode": 2
                    }
                  }
                ]
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Batch coding job accepted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchCodingResponse"
                },
                "example": {
                  "batchJobId": "123e4567-e89b-12d3-a456-426614174000",
                  "surveyIdentifier": "CSAT-2024-Q1",
                  "status": "queued",
                  "results": null
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid request parameters",
                  "details": {
                    "surveyIdentifier": "Survey identifier is required"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          },
          "504": {
            "description": "Gateway timeout",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "GATEWAY_TIMEOUT",
                  "message": "The server took too long to respond"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/coding/{batchJobId}": {
      "get": {
        "tags": ["Coding"],
        "summary": "Get batch coding job status",
        "description": "Retrieves the current status and results of a batch coding job",
        "operationId": "getBatchCodingJobStatus",
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
            "source": "const response = await api.coding.getBatchJobStatus('123e4567-e89b-12d3-a456-426614174000');"
          },
          {
            "lang": "Python",
            "source": "response = api.coding.get_batch_job_status('123e4567-e89b-12d3-a456-426614174000')"
          }
        ],
        "parameters": [
          {
            "name": "batchJobId",
            "in": "path",
            "required": true,
            "description": "ID of the batch coding job to check",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Batch coding job status retrieved successfully",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchCodingResponse"
                },
                "example": {
                  "batchJobId": "123e4567-e89b-12d3-a456-426614174000",
                  "surveyIdentifier": "CSAT-2024-Q1",
                  "status": "completed",
                  "results": {
                    "completedAt": "2024-03-12T15:30:45Z",
                    "questionCodes": [
                      {
                        "questionIdentifier": "Q1",
                        "question": "What did you like about our service?",
                        "responseCodes": [
                          {
                            "id": 1,
                            "label": "Customer Service Quality",
                            "responses": [
                              {
                                "responseIdentifier": "12345",
                                "answer": "The customer service representatives were very helpful and resolved my issue quickly."
                              }
                            ],
                            "subCodes": [
                              {
                                "id": 11,
                                "label": "Staff Helpfulness",
                                "responses": [
                                  {
                                    "responseIdentifier": "12345",
                                    "answer": "The customer service representatives were very helpful and resolved my issue quickly."
                                  }
                                ],
                                "subCodes": []
                              }
                            ]
                          },
                          {
                            "id": 2,
                            "label": "Delivery",
                            "responses": [
                              {
                                "responseIdentifier": "12346",
                                "answer": "I liked the easy-to-use website and fast delivery."
                              }
                            ],
                            "subCodes": []
                          }
                        ]
                      }
                    ],
                    "nextCursor": null
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid batch job ID format"
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "404": {
            "description": "Resource not found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "NOT_FOUND",
                  "message": "Batch job not found"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          },
          "504": {
            "description": "Gateway timeout",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "GATEWAY_TIMEOUT",
                  "message": "The server took too long to respond"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/brand-coding": {
      "post": {
        "tags": ["Coding"],
        "summary": "Create a brand coding job",
        "description": "Analyze survey responses in the context of specified brands and code them into hierarchical categories",
        "operationId": "createBrandCodingJob",
        "security": [
          {
            "ApiKeyAuth": []
          }
        ],
        "x-codeSamples": [
          {
            "lang": "JavaScript",
            "source": "const response = await api.coding.createBrandJob({\n  surveyIdentifier: 'CSAT-2024-Q1',\n  surveyName: 'Customer Satisfaction',\n  surveyDescription: 'Tracking customer satisfaction and loyalty',\n  surveyResponses: [\n    {\n      questionIdentifier: 'Q1',\n      question: 'What did you like about our service?',\n      brandContext: {\n        industryDescription: 'E-commerce retail',\n        brands: [\n          { name: 'Acme Store', variations: ['Acme', 'AcmeOnline'] }\n        ]\n      },\n      responseEntries: [\n        {\n          responseIdentifier: '12345',\n          answer: 'The customer service representatives were very helpful.',\n          followupResponses: [\n            { question: 'Which rep assisted you?', answer: 'Alice from support' }\n          ]\n        }\n      ]\n    }\n  ]\n});"
          },
          {
            "lang": "Python",
            "source": "response = api.coding.create_brand_job(\n    survey_identifier='CSAT-2024-Q1',\n    survey_name='Customer Satisfaction',\n    survey_description='Tracking customer satisfaction and loyalty',\n    survey_responses=[{\n        'question_identifier': 'Q1',\n        'question': 'What did you like about our service?',\n        'brand_context': {\n            'industry_description': 'E-commerce retail',\n            'brands': [\n                {'name': 'Acme Store', 'variations': ['Acme', 'AcmeOnline']}\n            ]\n        },\n        'response_entries': [\n            {\n                'response_identifier': '12345',\n                'answer': 'The customer service representatives were very helpful.',\n                'followup_responses': [\n                    {'question': 'Which rep assisted you?', 'answer': 'Alice from support'}\n                ]\n            }\n        ]\n    }]\n)"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchCodingRequest"
              },
              "example": {
                "surveyIdentifier": "CSAT-2024-Q1",
                "surveyName": "Customer Satisfaction",
                "surveyDescription": "Tracking customer satisfaction and loyalty for the XYZ Company",
                "surveyResponses": [
                  {
                    "questionIdentifier": "Q1",
                    "question": "What did you like about our service?",
                    "brandContext": {
                      "industryDescription": "E-commerce retail",
                      "brands": [
                        {
                          "name": "Acme Store",
                          "variations": ["Acme", "AcmeOnline"]
                        }
                      ]
                    },
                    "responseEntries": [
                      {
                        "responseIdentifier": "12345",
                        "answer": "The customer service representatives were very helpful and resolved my issue quickly.",
                        "followupResponses": [
                          {
                            "question": "Which feature was most important?",
                            "answer": "Fast shipping"
                          }
                        ]
                      },
                      {
                        "responseIdentifier": "12346",
                        "answer": "I liked the easy-to-use website and fast delivery."
                      }
                    ]
                  }
                ]
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Brand coding job accepted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchCodingResponse"
                },
                "example": {
                  "batchJobId": "123e4567-e89b-12d3-a456-426614174001",
                  "surveyIdentifier": "CSAT-2024-Q1",
                  "status": "queued",
                  "results": null
                }
              }
            }
          },
          "400": {
            "description": "Bad request - invalid input parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_REQUEST",
                  "message": "Invalid request parameters",
                  "details": {
                    "brandContext": "industryDescription is required"
                  }
                }
              }
            }
          },
          "403": {
            "description": "Forbidden - Missing or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INVALID_API_KEY",
                  "message": "Invalid or missing API key"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "INTERNAL_ERROR",
                  "message": "An unexpected error occurred"
                }
              }
            }
          },
          "504": {
            "description": "Gateway timeout",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "code": "GATEWAY_TIMEOUT",
                  "message": "The server took too long to respond"
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "ApiKeyAuth": {
        "type": "apiKey",
        "in": "header",
        "name": "X-Aftercare-Key",
        "description": "API key for authentication"
      }
    },
    "parameters": {
      "X-Request-Encoding": {
        "in": "header",
        "name": "X-Request-Encoding",
        "schema": {
          "type": "string",
          "enum": ["unicode", "html"],
          "default": "unicode"
        },
        "required": false,
        "description": "Specifies the encoding format of the request data. Use `html` if you are sending data that HTML entity encodes non-ASCII characters."
      },
      "X-Response-Encoding": {
        "in": "header",
        "name": "X-Response-Encoding",
        "schema": {
          "type": "string",
          "enum": ["unicode", "html"],
          "default": "unicode"
        },
        "required": false,
        "description": "Specifies the preferred encoding format for the response data. Use `html` if you are expecting to receive data that HTML entity encodes non-ASCII characters."
      }
    },
    "schemas": {
      "BrandContext": {
        "type": "object",
        "required": ["industryDescription","brands"],
        "properties": {
          "industryDescription": {
            "type": "string",
            "description": "Description of the industry the brand is in",
            "example": "Consumer electronics"
          },
          "brands": {
            "type": "array",
            "description": "Common names for the brand and any variations",
            "items": {
              "type": "object",
              "required": ["name"],
              "properties": {
                "name": {
                  "type": "string",
                  "description": "Canonical brand name",
                  "example": "Acme Corp"
                },
                "variations": {
                  "type": "array",
                  "items": { "type": "string" },
                  "description": "Alternative names or spellings",
                  "example": ["ACME", "Acme Corporation"]
                }
              }
            }
          }
        }
      },
      "FollowupResponse": {
        "type": "object",
        "required": ["question","answer"],
        "properties": {
          "question": {
            "type": "string",
            "description": "The follow-up question that was asked",
            "example": "What features of our product stood out most?"
          },
          "answer": {
            "type": "string",
            "description": "The answer provided to the follow-up",
            "example": "I loved the night-vision mode."
          }
        }
      },
      "FollowupGenerationGuidanceBehavior": {
        "type": "string",
        "description": "Different ways Aftercare AI will generate follow-up questions based on incomplete or irrelevant user input.\n\n* `Succinct` - The AI will not generate a follow-up question if the response is irrelevant or complete. This occurs when the relevance score is below 25 or the completeness score is above 70. This is the default behavior.\n* `Redirection` - The AI will return a follow-up question that redirects the user to answering the top-level question if it is irrelevant and incomplete.\nA follow-up question will be generated as long as the completeness score is below 70.\n* `Verbose` - The AI will always return a follow-up question regardless of the relevance or completeness of the response.",
        "enum": ["Succinct", "Redirection", "Verbose"],
        "default": "Succinct"
      },
      "ResponseEvaluation": {
        "type": "object",
        "required": ["completeness", "relevance"],
        "properties": {
          "completeness": {
            "type": "number",
            "description": "A number between 0 and 100 that represents how completely the response answered the topic question.\nThe higher the score, the more complete the response.",
            "minimum": 0,
            "maximum": 100
          },
          "relevance": {
            "type": "number",
            "description": "A number between 0 and 100 that represents the relevance of the response to the topic question.\nThe higher the score, the more relevant the response.",
            "minimum": 0,
            "maximum": 100
          }
        }
      },
      "FollowupGenerationRequest": {
        "type": "object",
        "required": [
          "question",
          "answer"
        ],
        "properties": {
          "surveyName": {
            "type": "string",
            "description": "The name of the survey as it will appear in the Aftercare platform",
            "example": "Customer Satisfaction"
          },
          "surveyDescription": {
            "type": "string",
            "description": "A description of the survey purpose and background.\n\nIt will be used to give the AI more context around specific aspects of the survey (e.g. brand/product names, movie names, etc.)",
            "example": "Quarterly survey tracking customer satisfaction and loyalty for the XYZ Company"
          },
          "question": {
            "type": "string",
            "description": "The question that was asked to the respondent",
            "example": "How likely are you to recommend our service?"
          },
          "questionContext": {
            "type": "string",
            "description": "A description of what you are trying to learn from the respondent for this question.\n\nThis will be used to give the AI guidance on what followup questions to ask.",
            "example": "I want to understand specifically why a customer is convinced to recommend our service. If they are not recommending our service, I want to know why."
          },
          "answer": {
            "type": "string",
            "description": "The answer to the question provided by the respondent",
            "example": "Very likely, the customer service is excellent"
          },
          "surveyIdentifiers": {
            "type": "object",
            "description": "Optional identifiers to tie responses to a specific survey and question.\nIf provided, Aftercare will use these to generate analytics over your survey responses.\n\nIf included, both survey and question identifiers are required.\n\nSee the [Aftercare Data Model](/aftercareDataModel) to learn more.",
            "required": ["surveyIdentifier", "questionIdentifier"],
            "properties": {
              "surveyIdentifier": {
                "type": "string",
                "description": "Optional unique identifier for the survey.\n\nAftercare will use this to build a data model to associate questions and answers with the survey.",
                "example": "CSAT-2024-Q1"
              },
              "questionIdentifier": {
                "type": "string",
                "description": "Optional unique identifier for the question.\n\nAftercare will use this to build a data model to track questions across a survey",
                "example": "Q1"
              }
            }
          },
          "responseLanguage": {
            "type": "string",
            "description": "Optional language to use for the followup question generation.\n\nIf not provided, Aftercare will default to the language it determines best matches the response.\n\nSet response language to `match_response_language` to automatically set the language of the generated follow up question to the language of the respondent's answer.",
            "example": "French"
          },
          "threadId": {
            "type": "string",
            "description": "A unique identifier for the follow-up response thread.\n\nIf provided, Aftercare will follow-up questions and answers in a thread with the original question and answer.\n\nIf not provided, Aftercare will automatically generate a new thread id you can use in a subsequent follow-up.",
            "example": "7a54b8da-f65d-4946-9c9a-f202e0cc29c8"
          },
          "responseIdentifier": {
            "type": "string",
            "description": "Optional unique identifier for a respondent's entire response to a survey.\n\nAftercare will use this to build a data model tie together questions and answer pairs for a single response.",
            "example": "12345"
          },
          "guidanceBehavior": {
            "$ref": "#/components/schemas/FollowupGenerationGuidanceBehavior"
          }
        }
      },
      "FollowupGenerationResponse": {
        "type": "object",
        "required": [
          "followupQuestion",
          "responseEvaluation"
        ],
        "properties": {
          "followupQuestion": {
            "type": "string",
            "description": "The generated followup question",
            "example": "What specific aspects of our customer service impressed you the most?"
          },
          "responseEvaluation": {
            "$ref": "#/components/schemas/ResponseEvaluation"
          },
          "threadId": {
            "type": "string",
            "description": "The unique identifier for the follow-up thread",
            "example": "7a54b8da-f65d-4946-9c9a-f202e0cc29c8"
          },
          "responseIdentifier": {
            "type": "string",
            "description": "Optional identifier for the survey response",
            "example": "12345"
          }
        }
      },
      
      "Error": {
        "type": "object",
        "required": [
          "code",
          "message"
        ],
        "properties": {
          "code": {
            "type": "string",
            "description": "Error code",
            "example": "INVALID_REQUEST"
          },
          "message": {
            "type": "string",
            "description": "Error message",
            "example": "Invalid request parameters"
          },
          "details": {
            "type": "object",
            "description": "Additional error details",
            "example": {
              "question": "Question is required"
            }
          }
        }
      },
      "QualityIssueType": {
        "type": "string",
        "enum": ["Nonsensical", "Irrelevant", "Low Effort", "LLM Generated", "Repeated Answers", "Duplicate Answers"],
        "description": "Types of quality issues that can be detected in survey responses.\n\n* `Nonsensical` - Response lacks logical meaning or sense. Likely gibberish.\n* `Irrelevant` - Response does not address the question.\n* `Low Effort` - Respondent did not put in much effort to answer the question. Lacks detail or concrete examples.\n* `LLM Generated` - Response appears to be generated by AI.\n* `Self Duplicated` - Responses from the same respondent contain duplicated content across multiple answers. Only evaluated when multiple survey entries are provided or if a survey identifier and response identifier is provided.\n* `Shared Duplicate` - Responses contain duplicated content across different respondents for the same question. Only evaluated if survey identifiers and question identifiers are provided."
      },
      "QualityDetectionMode": {
        "type": "string",
        "enum": ["Responsiveness", "Authenticity", "Composite"],
        "description": "The mode in which Aftercare will evaluate the quality of the survey responses.\n\n* `Responsiveness` - Checks for poor responses\n* `Authenticity` - Checks for fraudulent responses\n* `Composite` - Checks for all quality issues\n\nIf both a detectionMode and qualityIssues are provided, Aftercare will use the detection mode."
      },
      "BatchJobStatus": {
        "type": "string",
        "enum": ["queued", "processing", "completed", "failed"],
        "description": "Status values for batch processing jobs"
      },
      "SurveyEntryPaste": {
        "type": "object",
        "required": ["t", "c"],
        "properties": {
          "t": {
            "type": "number",
            "description": "Timestamp of the paste event"
          },
          "c": {
            "type": "string",
            "description": "Clipboard content that was pasted"
          }
        }
      },
      "SurveyEntryKeyStroke": {
        "type": "object",
        "required": ["k", "t", "ht", "c"],
        "properties": {
          "k": {
            "type": "string",
            "description": "Key value (e.g., \"a\", \"Enter\")"
          },
          "t": {
            "type": "number",
            "description": "Keydown timestamp (from performance.now())"
          },
          "ht": {
            "type": "number",
            "description": "Hold time of the key"
          },
          "c": {
            "type": "string",
            "description": "Physical key code (e.g., \"KeyA\", \"Enter\")"
          }
        }
      },
      "SurveyEntry": {
        "type": "object",
        "required": ["question", "answer"],
        "properties": {
          "question": {
            "type": "string",
            "description": "The question that was asked to the respondent"
          },
          "questionContext": {
            "type": "string",
            "description": "A description of what you are trying to learn from the respondent for this question"
          },
          "answer": {
            "type": "string",
            "description": "The answer to the question provided by the respondent"
          },
          "questionIdentifier": {
            "type": "string",
            "description": "Optional unique identifier for the question.\n\nAftercare will use this to build a data model to track questions across a survey"
          },
          "parentQuestionIdentifier": {
            "type": "string",
            "description": "Optional identifier of a previous question in a follow-up thread"
          },
          "keyEvents": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SurveyEntryKeyStroke"
            },
            "description": "An optional array of key strokes."
          },
          "pasteEvents": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SurveyEntryPaste"
            },
            "description": "An optional array of paste events."
          },
          "honeypotPhrase": {
            "type": "string",
            "description": "Optional string. If provided, Aftercare will check if the response contains any honey pot words."
          }
        }
      },
      "QualityIssueCheck": {
        "type": "object",
        "required": ["type", "score", "isIssue"],
        "properties": {
          "type": {
            "$ref": "#/components/schemas/QualityIssueType"
          },
          "score": {
            "type": "number",
            "description": "Score between 0-100 for this quality issue.\n\nThe higher the score, the greater the likelihood and severity of the quality issue.",
            "minimum": 0,
            "maximum": 100
          },
          "isIssue": {
            "type": "boolean",
            "description": "Indicates if this issue was detected"
          },
          "evidence": {
            "type": "string",
            "description": " An optional string, evidence provides the reason for the quality issue score."
          }
        }
      },
      "SurveyEntryEvaluation": {
        "type": "object",
        "required": ["surveyEntry", "numIssues", "qualityScore", "demeritScore", "qualityIssueChecks"],
        "properties": {
          "surveyEntry": {
            "$ref": "#/components/schemas/SurveyEntry"
          },
          "numIssues": {
            "type": "integer",
            "description": "Number of quality issues detected",
            "minimum": 0
          },
          "hasIssues": {
            "type": "boolean",
            "description": "If Aftercare has detected any quality issues for this survey entry"
          },
          "qualityScore": {
            "type": "number",
            "description": "A score between 0 and 100 that represents the overall quality of the individual survey entry. (Deprecated: use demeritScore instead)",
            "minimum": 0,
            "maximum": 100,
            "deprecated": true
          },
          "demeritScore": {
            "type": "number",
            "description": "A score between 0 and 100 that represents the overall quality of the individual survey entry.\n\nThe score is a weighted average of the quality issue scores.\n\nThe higher the score, the greater the likelihood and severity of data quality issues.",
            "minimum": 0,
            "maximum": 100
          },
          "qualityIssueChecks": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/QualityIssueCheck"
            }
          }
        }
      },
      "DataQualityRequest": {
        "type": "object",
        "required": ["surveyEntries"],
        "properties": {
          "surveyName": {
            "type": "string",
            "description": "The name of the survey as it will appear in the Aftercare platform"
          },
          "surveyDescription": {
            "type": "string",
            "description": "A description of the survey purpose and background.\n\nIt will be used to give the AI more context around specific aspects of the survey (e.g. brand/product names, movie names, etc.)"
          },
          "surveyEntries": {
            "type": "array",
            "description": "The collection of question-answer pairs to evaluate.\n\nIf a respondent does not answer a question, DO NOT include that question in the surveyEntries array.",
            "items": {
              "$ref": "#/components/schemas/SurveyEntry"
            }
          },
          "surveyIdentifier": {
            "type": "string",
            "description": "Optional unique identifier for the survey.\n\nAftercare will use this to build a data model to associate questions and answers with the survey."
          },
          "responseIdentifier": {
            "type": "string",
            "description": "Optional unique identifier for a respondent's entire response to a survey.\n\nAftercare will use this to build a data model tie together questions and answer pairs for a single response."
          },
          "aftercareResponseIdentifier": {
            "type": "number",
            "description": "Optional unique identifier for the survey response. If not provided, Aftercare will generate one.\n\nThis identifier is useful for tracking survey responses that are submitted in multiple parts or over time.\n\nIf both a responseIdentifier and aftercareResponseIdentifier are provided, Aftercare will use the aftercareResponseIdentifier."
          },
          "qualityIssues": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/QualityIssueType"
            },
            "description": "Optional array of specific quality issues to evaluate. If not provided, all applicable quality issues will be checked."
          },
          "detectionMode": {
            "$ref": "#/components/schemas/QualityDetectionMode"
          }
        }
      },
      "DataQualityResponse": {
        "type": "object",
        "required": ["numIssues", "qualityScore", "demeritScore", "evaluations", "aftercareResponseIdentifier"],
        "properties": {
          "numIssues": {
            "type": "integer",
            "description": "Number of quality issues detected across all survey entries",
            "minimum": 0
          },
          "hasIssues": {
            "type": "boolean",
            "description": "If Aftercare has detected any quality issues for this response"
          },
          "qualityScore": {
            "type": "number",
            "description": "A score between 0 and 100 that represents the overall quality of the survey response. (Deprecated: use demeritScore instead)",
            "minimum": 0,
            "maximum": 100
          },
          "demeritScore": {
            "type": "number",
            "description": "A score between 0 and 100 that represents the overall quality of the survey response.\n\nThe score is an average of the quality scores across all survey entries.\n\nThe higher the score, the greater the likelihood and severity of data quality issues.",
            "minimum": 0,
            "maximum": 100
          },
          "evaluations": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SurveyEntryEvaluation"
            }
          },
          "aftercareResponseIdentifier": {
            "type": "number",
            "description": "Unique identifier for the survey response generated by Aftercare"
          }
        }
      },
      "SurveyResponse": {
        "type": "object",
        "required": ["surveyEntries"],
        "properties": {
          "responseIdentifier": {
            "type": "string",
            "description": "Optional identifier for the survey response. Aftercare can use this to asscociate survey entries for a single response.\n\nIf a response identifier is not provided, Aftercare will generate one and return it in the response - useful if the survey response is submitted in multiple parts or submitted over time."
          },
          "surveyEntries": {
            "type": "array",
            "description": "The collection of question-answer pairs to evaluate.\n\nIf a respondent does not answer a question, DO NOT include that question in the surveyEntries array.",
            "items": {
              "$ref": "#/components/schemas/SurveyEntry"
            }
          }
        }
      },
      "DataQualityBatchRequest": {
        "type": "object",
        "required": ["surveyName", "responses", "callbackUrl"],
        "properties": {
          "surveyName": {
            "type": "string",
            "description": "The name of the survey"
          },
          "surveyIdentifier": {
            "type": "string",
            "description": "Optional unique identifier for the survey.\n\nAftercare will use this to build a data model to associate questions and answers with the survey."
          },
          "surveyDescription": {
            "type": "string",
            "description": "A description of the survey purpose and background."
          },
          "responses": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SurveyResponse"
            }
          },
          "qualityIssues": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/QualityIssueType"
            },
            "description": "Optional array of specific quality issues to evaluate. If not provided, all applicable quality issues will be checked."
          },
          "detectionMode": {
            "$ref": "#/components/schemas/QualityDetectionMode"
          },
          "callbackUrl": {
            "type": "string",
            "description": "URL where results should be sent when processing completes"
          }
        }
      },
      "BatchCodingRequest": {
        "type": "object",
        "required": ["surveyIdentifier", "surveyResponses"],
        "properties": {
          "surveyIdentifier": {
            "type": "string",
            "description": "Unique string to identify the survey.",
            "example": "CSAT-2024-Q1"
          },
          "surveyName": {
            "type": "string",
            "description": "Optional name for the survey. This is used to identify the survey in the Aftercare platform.",
            "example": "Customer Satisfaction"
          },
          "surveyDescription": {
            "type": "string",
            "description": "An optional description of the survey's purpose, used to help the AI understand the context behind thesurvey better.",
            "example": "Quarterly survey tracking customer satisfaction and loyalty for the XYZ Company which sells xyz products"
          },
          "surveyResponses": {
            "type": "array",
            "description": "Full collection of survey responses by question.",
            "items": {
              "$ref": "#/components/schemas/SurveyQuestionData"
            }
          }
        }
      },
      "SurveyQuestionData": {
        "type": "object",
        "required": ["questionIdentifier","question","brandContext","responseEntries"],
        "properties": {
          "questionIdentifier": {
            "type": "string",
            "description": "Unique identifier for the question",
            "example": "q1"
          },
          "question": {
            "type": "string",
            "description": "The question that was asked",
            "example": "What do you like about our product?"
          },
          "brandContext": {
            "$ref": "#/components/schemas/BrandContext",
            "description": "Additional context about the brands for this question"
          },
          "responseEntries": {
            "type": "array",
            "items": { "$ref": "#/components/schemas/ResponseEntry" }
          }
        }
      },
      "CodingOptions": {
        "type": "object",
        "properties": {
          "maxLevels": {
            "type": "integer",
            "description": "The maximum number of levels of categorization allowed. For example, if you only want codes and subcodes, set maxLevels to 2. Default: 2",
            "example": 3,
            "minimum": 1
          },
          "maxCodesPerLevel": {
            "oneOf": [
              {
                "type": "integer",
                "minimum": 1
              },
              {
                "type": "array",
                "items": {
                  "type": "integer",
                  "minimum": 1
                }
              }
            ],
            "description": "The maximum number of codes to create at each level of the hierarchy. If you provide a single number, the same max will be applied to all levels. If you provide an array, the number of codes allowed at each level will be the value at that index. Default: 8",
            "example": [8, 5, 3]
          },
          "minResponsesPerCode": {
            "type": "integer",
            "description": "The minimum number of responses that must be present to form a new code. Default: 1",
            "example": 2,
            "minimum": 1
          }
        }
      },
      "BatchJobResults": {
        "type": "object",
        "required": ["items"],
        "properties": {
          "items": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/RespondentEvaluation"
            }
          },
          "nextCursor": {
            "type": "string",
            "nullable": true,
            "description": "Cursor for the next page of results"
          }
        }
      },
      "RespondentEvaluation": {
        "type": "object",
        "required": ["numIssues", "qualityScore", "demeritScore", "evaluations"],
        "properties": {
          "responseIdentifier": {
            "type": "string",
            "description": "Optional identifier for the survey response. Aftercare can use this to asscociate survey entries for a single response.\n\nIf a response identifier is not provided, Aftercare will generate one."
          },
          "numIssues": {
            "type": "integer",
            "description": "Number of quality issues detected",
            "minimum": 0
          },
          "qualityScore": {
            "type": "number",
            "description": "A score between 0 and 100 that represents the overall quality of the survey response.\n\nThe score is an average of the quality scores across all survey entries.\n\nThe lower the score, the greater the likelihood and severity of data quality issues.",
            "minimum": 0,
            "maximum": 100
          },
          "demeritScore": {
            "type": "number",
            "description": "A score between 0 and 100 that represents the overall quality of the survey response.\n\nThe score is an average of the quality scores across all survey entries.\n\nThe higher the score, the greater the likelihood and severity of data quality issues.",
            "minimum": 0,
            "maximum": 100
          },
          "evaluations": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SurveyEntryEvaluation"
            }
          }
        }
      },
      "DataQualityBatchResponse": {
        "type": "object",
        "required": ["batchJobId", "status"],
        "properties": {
          "batchJobId": {
            "type": "string",
            "description": "Unique identifier for the batch processing job"
          },
          "status": {
            "$ref": "#/components/schemas/BatchJobStatus"
          },
          "results": {
            "$ref": "#/components/schemas/BatchJobResults"
          }
        }
      },
      "BatchCodingSuccess": {
        "type": "object",
        "required": ["completedAt", "questionCodes"],
        "properties": {
          "completedAt": {
            "type": "string",
            "format": "date-time",
            "description": "When the batch job completed processing",
            "example": "2024-03-12T15:30:45Z"
          },
          "questionCodes": {
            "type": "array",
            "description": "Coding results organized by question identifier. Each question will have its own hierarchical category tree.",
            "items": {
              "$ref": "#/components/schemas/QuestionCodeData"
            }
          },
          "nextCursor": {
            "type": "string",
            "nullable": true,
            "description": "Cursor for the next page of results. Null if there are no more results.",
            "example": null
          }
        }
      },
      "BatchCodingStatus": {
        "type": "string",
        "enum": ["queued", "processing", "completed", "partial_failure", "total_failure"],
        "description": "Status values for the batch processing job.\n\n* `queued` - Job has been received but processing has not yet started\n* `processing` - Job is currently being processed\n* `completed` - Job has finished processing successfully\n* `partial_failure` - Job has finished processing with some failures\n* `total_failure` - Job encountered an error during processing and did not complete any results."
      },
      "BatchCodingErrorDetails": {
        "type": "object",
        "required": ["code", "message"],
        "properties": {
          "code": {
            "type": "string",
            "description": "Error code identifying the type of failure",
            "example": "PROCESSING_ERROR"
          },
          "message": {
            "type": "string",
            "description": "Description of the error",
            "example": "Failed to process survey responses"
          }
        }
      },
      "QuestionCodeData": {
        "type": "object",
        "required": ["questionIdentifier", "question", "responseCodes"],
        "properties": {
          "questionIdentifier": {
            "type": "string",
            "description": "Unique identifier for the question.",
            "example": "Q1"
          },
          "question": {
            "type": "string",
            "description": "The question text.",
            "example": "What did you like about our service?"
          },
          "responseCodes": {
            "type": "array",
            "description": "Hierarchical code tree for this specific question. Codes can have subcodes forming a tree structure.",
            "items": {
              "$ref": "#/components/schemas/ResponseCode"
            }
          }
        }
      },
      "BatchCodingResponse": {
        "type": "object",
        "required": ["batchJobId", "surveyIdentifier", "status"],
        "properties": {
          "batchJobId": {
            "type": "string",
            "description": "Unique identifier for the coding job",
            "example": "123e4567-e89b-12d3-a456-426614174000"
          },
          "surveyIdentifier": {
            "type": "string",
            "description": "Unique identifier for the survey",
            "example": "CSAT-2024-Q1"
          },
          "status": {
            "$ref": "#/components/schemas/BatchCodingStatus",
            "description": "Status of the batch job that determines the structure of results"
          },
          "results": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/BatchCodingSuccess",
                "title": "Success Response",
                "description": "Present when status is 'completed'"
              },
              {
                "$ref": "#/components/schemas/BatchCodingErrorDetails",
                "title": "Error Response",
                "description": "Present when status is 'partial_failure' or 'total_failure'"
              }
            ],
            "description": "The results structure depends on the status value. If the job is successful, the results will be a list of question codes with a hierarchical tree of codes and subcodes. If the job fails, the results will be the error details.",
            "discriminator": {
              "propertyName": "status",
              "mapping": {
                "completed": "#/components/schemas/BatchCodingSuccess",
                "partial_failure": "#/components/schemas/BatchCodingErrorDetails",
                "total_failure": "#/components/schemas/BatchCodingErrorDetails"
              }
            }
          }
        }
      },
      "ResponseCode": {
        "type": "object",
        "required": ["id", "label", "responses", "subCodes"],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier for this code",
            "example": 1
          },
          "label": {
            "type": "string",
            "description": "Label of the code",
            "example": "Customer Service Quality"
          },
          "responses": {
            "type": "array",
            "description": "The responses that were classified into this code",
            "items": {
              "$ref": "#/components/schemas/ResponseEntry"
            }
          },
          "subCodes": {
            "type": "array",
            "description": "More specific codes classified under this code that can be used to further classify the responses",
            "items": {
              "$ref": "#/components/schemas/ResponseCode"
            }
          }
        }
      },
      "ResponseEntry": {
        "type": "object",
        "required": ["responseIdentifier","answer"],
        "properties": {
          "responseIdentifier": {
            "type": "string",
            "description": "Unique identifier for this response entry",
            "example": "resp-123"
          },
          "answer": {
            "type": "string",
            "description": "The respondent's answer to the question",
            "example": "I really enjoy the battery life."
          },
          "followupResponses": {
            "type": "array",
            "description": "Any follow-up question/answer pairs for this response",
            "items": { "$ref": "#/components/schemas/FollowupResponse" }
          }
        }
      }
    }
  }
}