QuantixAI API Documentation

Programmatic access to QuantixAI data ingestion, causal impact analysis, and forecasting. All endpoints are documented below per service.

Data API

The Data API lets you upload datasets in JSON format for downstream analysis and forecasting. Use this API to integrate your internal systems or pipelines with QuantixAI’s secure data layer.

Base URL

Base URL: https://data.quantix-ai.eu

Authentication

All requests must include a valid API key. Include the key in the Authorization header using the Bearer scheme.

  • Header: Authorization: Bearer <your_api_key>

Endpoints

POST /api/v1/data/upload

Upload a dataset as a JSON payload. The uploaded dataset will be stored and made available for analysis and forecasting. If a dataset with the same name exists, set overwrite accordingly.

Request Body

Field Type Required Description
name string Yes Name for your dataset.
data object Yes Column‑oriented representation of your dataset as key/value pairs. Each key is a column name and each value is an array of values.
description string No Optional description of the dataset.
preserve boolean No If true, the dataset will not be auto‑deleted. Default: false.
overwrite boolean No If true, replaces an existing dataset with the same name. Default: true.

Example Request

curl -X POST https://data.quantix-ai.eu/api/v1/data/upload \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Sales Data Q4",
    "description": "Quarterly sales report",
    "preserve": true,
    "data": {
      "date": ["2024-01-01", "2024-01-02", "2024-01-03"],
      "sales": [100, 150, 200],
      "region": ["North", "South", "East"]
    }
  }'

Success Response

{
  "success": true,
  "file_id": "abc123def456",
  "message": "Data uploaded successfully"
}

Error Responses

Status Meaning Typical Cause
401 Unauthorized API key missing or invalid. Missing Authorization header, or wrong key.
403 Forbidden Your API key does not have permission to upload data. Key lacks the necessary scope.
404 Not Found The requested dataset was not found. Incorrect dataset identifier.
409 Conflict A dataset with the same name already exists. Set overwrite=true to replace it.
400 Bad Request Missing required fields or invalid data format. Ensure name and data are provided and correctly formatted.
500 Internal Server Error Unexpected error on the server. Retry later or contact support.

Causal Impact API

The Causal Impact API quantifies the incremental impact of an intervention (e.g. marketing campaign, pricing change or product launch) on a time series metric using Bayesian structural time‑series models.

Base URL

Base URL: https://ci.quantix-ai.eu

Authentication

All requests must include your QuantixAI API key. The key must have the causal_impact scope.

  • Header: Authorization: Bearer <your_api_key>

Endpoints

POST /causalimpact

Runs a causal impact analysis on your time series data. Provide the response variable and optional covariates, along with pre‑ and post‑intervention periods and seasonality settings.

Request Body (JSON)

Field Type Required Description
data object/array Yes Time series data where the first column (y) is the response variable and any additional columns (x1, x2, …) are covariates (controls).
preperiod array<2> Yes Pre‑intervention period indices as [start, end] (1‑indexed).
postperiod array<2> Yes Post‑intervention period indices as [start, end] (1‑indexed).
CI number No Confidence interval level; defaults to 0.95 for a 95% interval.
nseasons integer Yes Number of seasons in the time series (e.g. 7 for weekly data, 12 for monthly data, 1 for no seasonality).

Data Format

The data object should include the response variable under the key y and optional control series under keys like x1, x2, etc. Each key maps to an array of numeric values of equal length.

Example Request

POST /causalimpact
Host: causalimpact.quantix-ai.eu
Authorization: Bearer YOUR_API_KEY
Content-Type: application/json

{
  "data": {
    "y":  [100, 105, 110, 115, 108, 112, 120, 125, 130, 135],
    "x1": [50,  52,  51,  53,  55,  54,  56,  58,  57,  59]
  },
  "preperiod":  [1, 6],
  "postperiod": [7, 10],
  "CI": 0.95,
  "nseasons": 7
}

Success Response

The response contains a summary of the average and cumulative effects and a detailed series of predictions and effects.

{
  "summary": {
    "Metric": ["Actual", "Pred", "Pred.lower", "Pred.upper", ...],
    "Average": [150.5, 142.3, 138.1, 146.5, ...],
    "Cumulative": [1505, 1423, 1381, 1465, ...]
  },
  "series": {
    "response":         [100, 105, 110, 115, ...],
    "cum.response":     [100, 205, 315, ...],
    "point.pred":       [99.8, 105.2, 109.7, ...],
    "point.pred.lower": [95.1, 100.3, 104.8, ...],
    "point.pred.upper": [104.5, 110.1, 114.6, ...],
    "point.effect":     [0.2, -0.2, 0.3, ...],
    "cum.effect":       [0.2, 0.0, 0.3, ...]
    // Additional fields omitted for brevity
  }
}

Response Fields

Field Description
summary Statistical summary containing metrics for average and cumulative effects.
series.response Actual observed values of the response variable.
series.point.pred Predicted (counterfactual) values for each time point.
series.point.effect Point‑wise causal effect, computed as actual minus predicted.
series.cum.effect Cumulative causal effect over the post‑intervention period.
*.lower / *.upper Lower and upper bounds of the confidence intervals at the specified CI level.
GET /health

Basic health check endpoint for the Causal Impact API service.

Authentication

This endpoint does not require authentication.

Example Response

{
  "status": "OK",
  "timestamp": "2024-12-23 15:30:45",
  "database": "connected"
}

Error Responses

Status Meaning Typical Cause
401 Unauthorized API key missing or invalid. Missing Authorization header, invalid key or insufficient scope.
403 Forbidden API key does not have the required scope. The key is valid but lacks the causal_impact scope.
400 Bad Request Invalid timestamps, missing fields or malformed JSON. Incorrect preperiod / postperiod lengths, non‑numeric data, insufficient data points.
500 Internal Server Error Unexpected error during analysis. Retry later or contact support.

Forecast API

The Forecast API exposes QuantixAI’s time‑series forecasting engine. It supports asynchronous training and forecasting for both machine‑learning and classical statistical models, hierarchical reconciliation, scenario analysis, exogenous variables and automated outlier preprocessing.

Base URL

Base URL: https://forecast.quantix-ai.eu

Authentication

All endpoints require an API key. Include your key in the X-API-Key header.

  • Header: X-API-Key: <your_api_key>

Endpoints

Machine Learning Endpoints

POST /ml/train

Queue a training job for a machine‑learning forecasting model. Provide your time series data, the desired forecast horizon, data frequency and model metadata. Training runs asynchronously: the API returns a job_id immediately and automatically generates a model_id which you will use for forecasting and refitting. Poll the queue endpoints to track job progress.

Request Body

Field Type Required Description
data array Yes Array of objects with date (YYYY‑MM‑DD), target (numeric) and unique_id (series identifier). Include any exogenous or static feature columns alongside these required fields.
horizon integer Yes Number of future periods to forecast.
frequency integer Yes Data frequency: 7 (daily), 52 (weekly), 12 (monthly), 4 (quarterly) or 5 (yearly).
user_id string Yes Identifier of the user requesting the model.
model_name string Yes Human‑readable name to identify the model.
email string No Email address to notify when training completes.
exog_columns array No List of column names used as exogenous variables during training.
uses_exogenous boolean No Set to true when training with exogenous variables (default: false).
static_features array No List of categorical feature names for global models (e.g., store type, region).
level array No Prediction interval levels (e.g., [80, 95]).
apply_reconciliation boolean No Enable hierarchical reconciliation of forecasts (default: false).
reconciliation_spec array No Hierarchy specification for reconciliation. It should be an array of arrays, from the highest aggregation level to the most detailed. The final array must include all hierarchy columns, and the order determines how unique_id values are composed.
preprocessing_config object No Outlier detection and treatment configuration. Provide {"preset": "default"} to enable a preset or specify custom settings. If omitted, no preprocessing is applied. Preprocessing is only applied to models without exogenous variables; models with exogenous variables skip this step to preserve their external features.
ℹ️ Auto‑generated model ID:

The model_id is created by the API and returned in the response. Use this identifier for forecasting, refitting and scenario analysis.

⚠️ Hierarchy Structure Requirements:

If apply_reconciliation is true, the reconciliation_spec must follow these rules:

  • Order arrays from the highest level down to the most detailed.
  • The final array must contain all hierarchy columns.
  • The order of columns in the last array determines how unique_id values are constructed.

Response

{
  "job_id": "job_abc123",
  "message": "Training job queued successfully. Job ID: job_abc123",
  "model_id": "job_abc123",
  "status": "queued",
  "user_id": null,
  "metadata": {
    "status": "queued",
    "job_id": "job_abc123",
    "queue_position": 0,
    "estimated_wait_seconds": 30,
    "check_status_url": "/ml/job/job_abc123"
  }
}
POST /ml/forecast

Generate forecasts synchronously using a trained machine‑learning model. This endpoint blocks until completion and is intended for development or single‑user scenarios. Production systems should use /ml/forecast-async to avoid HTTP timeouts.

Request Body

Field Type Required Description
model_id string Yes ID of the trained model to use.
horizon integer Yes Number of future periods to forecast.
level array No Prediction interval levels (default: [80, 90]).
data array Conditional Future exogenous data and static features. Required only for models trained with exogenous variables. Provide exactly horizon rows per unique_id.
user_id string No Optional user identifier override (admin scope only). If omitted, the API key’s associated user is used.

Response

{
  "predictions": {
    "series1": [110.5, 115.2],
    "series2": [205.1, 210.3]
  },
  "model_id": "ml_abc123",
  "prediction_intervals": {
    "series1": {
      "lo-95": [100.2, 104.8],
      "hi-95": [120.8, 125.6]
    }
  },
  "fit_data": {
    "series1": {
      "dates": ["2023-06-01", "2023-07-01", "2023-08-01", "2023-09-01", "2023-10-01"],
      "values": [90, 92, 95, 98, 100]
    },
    "series2": {
      "dates": ["2023-06-01", "2023-07-01", "2023-08-01", "2023-09-01", "2023-10-01"],
      "values": [180, 185, 190, 195, 200]
    }
  }
}
POST /ml/forecast-async

Generate forecasts asynchronously using a trained ML model. This endpoint returns immediately with a job_id and is recommended for production applications.

Benefits

  • ✅ No HTTP timeouts – clients can poll for results.
  • ✅ Fair FIFO queueing for concurrent users.
  • ✅ Progress updates available via polling.
  • ✅ Scales to multiple concurrent users.

Request Body

Same parameters as /ml/forecast.

Initial Response

{
  "job_id": "abc123-def456-789",
  "status": "queued",
  "message": "Forecast job queued successfully",
  "metadata": {
    "queue_position": 2,
    "estimated_wait_seconds": 300,
    "estimated_wait_minutes": 5.0,
    "check_status_url": "/queue/job/abc123-def456-789"
  }
}
POST /refit

Refit an existing model with new data. This unified endpoint works for both ML and statistical models. It automatically detects the model type and updates model weights while preserving the original configuration (frequency, horizon, exogenous settings, static features and reconciliation structure). Use it to keep your model up‑to‑date without a full retraining.

Request Body

Field Type Required Description
model_id string Yes ID of the trained model to refit.
user_id string Yes User identifier.
data array Yes New training data. For hierarchical models provide bottom‑level (ungrouped) data. The API infers column names from stored metadata but you may override them using the optional fields below.
email string No Email address for completion notification.
unique_id_col string No Override the default unique_id column name.
date_col string No Override the default date column name.
target_col string No Override the default target column name.
ℹ️ Automatic configuration loading:

This endpoint automatically loads the model type (ML or statistical), frequency, horizon, exogenous variable configuration, static features, reconciliation settings and the best statistical model per series (for statistical models). Historical fit_data is saved to storage and cross‑validation metrics are recalculated.

Response

{
  "status": "queued",
  "job_id": "refit_job_abc123",
  "message": "ML refit job queued successfully",
  "model_id": "your_model_id",
  "model_type": "ML"
}
POST /ml/scenario-forecast-async

Generate multiple forecast scenarios asynchronously using different exogenous assumptions. Each row in the data array must specify a scenario label and include values for all exogenous variables used during training. This endpoint returns a job_id; poll the queue to retrieve results.

Request Body

Field Type Required Description
model_id string Yes ID of the trained model.
data array Yes Future exogenous values per scenario. Each entry must include a scenario identifier and all exogenous columns used in training.
horizon integer Yes Number of future periods to forecast.
level array No Prediction interval levels (default: [80, 90]).
user_id string No Optional user identifier override (admin only). Omit for default.
ℹ️ Simplified payload:

Exogenous settings (uses_exogenous, exog_columns), static features and historical data are loaded from the model metadata. You only need to provide future values per scenario; there is no “actual” scenario required.

Initial Response

{
  "job_id": "scenario_abc123-def456",
  "status": "queued",
  "message": "Scenario forecast job queued successfully"
}
POST /ml/scenario-forecast

Generate forecast scenarios synchronously. Accepts the same payload as /ml/scenario-forecast-async but returns the results directly. Intended for testing or single‑user environments.

Statistical Endpoints

POST /stats/train

Train classical statistical models on your time series. The API automatically trains multiple model types and selects the best model per series based on cross‑validation performance. Statistical training runs asynchronously and returns a job_id.

Request Body

Field Type Required Description
data array Yes Time series data with date, target and unique_id columns.
horizon integer Yes Number of future periods to forecast.
frequency integer Yes Data frequency (7, 52, 12, 4 or 5).
user_id string Yes Identifier of the user.
model_name string Yes Name for the statistical model ensemble.
email string No Email address for completion notification.
level array No Prediction interval levels.
apply_reconciliation boolean No Enable hierarchical reconciliation (default: false).
reconciliation_spec array No Hierarchy specification (same format as in ML training).
preprocessing_config object No Outlier detection and treatment configuration. Provide {"preset": "default"} to enable a preset or specify custom settings. If omitted or set to null, no preprocessing is applied. See the preprocessing section for details.
ℹ️ Auto‑generated model ID:

The model_id for statistical models is also generated automatically and returned in the response.

⚠️ Hierarchy Structure Requirements:

When using reconciliation, the reconciliation_spec must list levels from highest to lowest, include all hierarchy columns in the final level, and the column order defines unique_id construction.

Response

{
  "job_id": "job_stats_123",
  "message": "Training job queued successfully. Job ID: job_stats_123",
  "model_id": "job_stats_123",
  "status": "queued",
  "user_id": null,
  "metadata": {
    "status": "queued",
    "job_id": "job_stats_123",
    "queue_position": 2,
    "estimated_wait_seconds": 45,
    "check_status_url": "/ml/job/job_stats_123"
  }
}
POST /stats/forecast

Generate forecasts synchronously using a trained statistical model. For non‑exogenous models you need only the model_id and horizon. For reconciled models you may optionally supply future data with exactly horizon rows per series.

Request Body

Field Type Required Description
model_id string Yes ID of the trained statistical model.
horizon integer Yes Number of future periods to forecast.
level array No Prediction interval levels (default: [80, 90]).
data array No Future data for reconciled models. When provided, supply exactly horizon rows per unique_id. For non‑reconciled models omit this field.
user_id string No Optional user identifier override (admin only). Defaults to the API key’s user.

Response

{
    "predictions": {
        "series1": [110.5, 115.2],
        "series2": [205.1, 210.3]
    },
    "model_id": "stats_abc123",
    "prediction_intervals": {
        "series1": {
            "lo-95": [100.2, 104.8],
            "hi-95": [120.8, 125.6]
        }
    },
    "fit_data": {
        "series1": {
            "dates": ["2023-06-01", "2023-07-01", "2023-08-01", "2023-09-01", "2023-10-01"],
            "values": [90, 92, 95, 98, 100]
        },
        "series2": {
            "dates": ["2023-06-01", "2023-07-01", "2023-08-01", "2023-09-01", "2023-10-01"],
            "values": [180, 185, 190, 195, 200]
        }
    }
}
POST /stats/forecast-async

Generate forecasts asynchronously using a statistical model. This endpoint is recommended for production. The request body is the same as /stats/forecast.

Initial Response

{
  "job_id": "xyz789-abc123-456",
  "status": "queued",
  "message": "Forecast job queued successfully",
  "metadata": {
    "queue_position": 1,
    "estimated_wait_seconds": 180,
    "estimated_wait_minutes": 3.0,
    "check_status_url": "/queue/job/xyz789-abc123-456"
  }
}

Queue Management Endpoints

GET /queue/job/{job_id}

Retrieve the status and result of an asynchronous job. Poll this endpoint every 2–5 seconds until the job’s status becomes finished or failed.

Response

{
  "job_id": "job_xyz789",
  "status": "completed",
  "created_at": "2024-01-15T10:30:00Z",
  "completed_at": "2024-01-15T10:35:00Z",
  "result": {
    "forecast": [...]
  },
  "error": null
}

Job Statuses

  • queued – waiting in the queue
  • processing – currently being processed
  • completed – job completed successfully
  • failed – job failed (see error field for details)
GET /queue/stats

Retrieve statistics about all jobs in the queue, including counts of queued, processing, completed and failed jobs.

Response

{
  "total_jobs": 150,
  "queued": 5,
  "processing": 3,
  "completed": 140,
  "failed": 2
}
DELETE /queue/job/{job_id}

Cancel or delete a queued job. This action requires administrative privileges.

GET /queue/health

Health check endpoint for the queue service. Returns basic status information and does not require authentication.

Response

{
  "status": "healthy",
  "timestamp": "2024-01-15T10:30:00Z"
}
GET /docs

Returns the interactive documentation UI (for example, an OpenAPI/Swagger interface) for the Forecast API.

Data Format Requirements

All training and forecasting requests use the same basic structure for time series data. Each record must include a date, a numeric target value and a series identifier. You can optionally include exogenous variables and static features.

Input Data Structure

[
  {
    "date": "2024-01-01",   // Date in YYYY‑MM‑DD format
    "target": 100.5,          // Target value to forecast
    "unique_id": "series1",  // Identifier for the time series
    "temperature": 15.5,      // Exogenous variable (optional)
    "holiday": 1              // Exogenous variable (optional)
  },
  {
    "date": "2024-01-02",
    "target": 105.2,
    "unique_id": "series1",
    "temperature": 16.2,
    "holiday": 0
  }
]

Required Columns

Column Type Description
date string/date Timestamp in YYYY‑MM‑DD or YYYY‑MM‑DD HH:MM:SS format.
target number Numeric value of the target variable (the metric you want to forecast).
unique_id string Identifier for the time series. Use a unique value per series when forecasting multiple series.
ℹ️ Column name defaults:

You can override default column names using the optional date_col, target_col and unique_id_col parameters in your requests. If omitted, the API assumes date, target and unique_id.

Fit Data Response Format

Forecast responses include a fit_data section with the historical values used for model training. For each series the response may include either a simple array of numeric values (legacy format) or a structured object with separate dates and values arrays. The structured form is recommended.

{
  "fit_data": {
    "series1": {
      "dates": ["2023-06-01", "2023-07-01", "2023-08-01", "2023-09-01"],
      "values": [100.0, 102.5, 104.3, 107.8]
    }
  }
}

Frequency Values

ValueFrequencyExample
7DailyDaily sales data
52WeeklyWeekly traffic data
12MonthlyMonthly revenue
4QuarterlyQuarterly earnings
5YearlyAnnual GDP

Data Quality Requirements

  • Minimum length: Daily data should span at least 2–3 years; weekly at least 2 years; monthly at least 4 years; quarterly at least 6 years.
  • Missing values: The API interpolates missing values, but you should supply complete data whenever possible for best results.
  • Consistency: Provide regular time intervals with no large gaps.
  • Data types: Target values must be numeric; do not include strings in the target column.

Exogenous Variables

Exogenous variables (external features) can significantly improve forecast accuracy by incorporating additional context. The API supports numeric, categorical and binary exogenous variables.

Supported Variable Types

TypeDescriptionExample
NumericContinuous valuesTemperature, price, GDP
CategoricalDiscrete categoriesDay of week, season, product category
BinaryYes/No indicatorsHoliday, promotion, weekend

Historical Data with Exogenous Variables

{
  "data": [
    {
      "date": "2024-01-01",
      "target": 100,
      "unique_id": "series1",
      "temperature": 15.5,
      "holiday": 1,
      "promotion": 0
    }
  ],
  "exog_columns": ["temperature", "holiday", "promotion"],
  "uses_exogenous": true
}

Future Exogenous Values

When forecasting with exogenous variables you must supply future values for the entire forecast horizon:

{
  "data": [
    {
      "date": "2024-07-01",
      "unique_id": "series1",
      "temperature": 25.0,
      "holiday": 0,
      "promotion": 1
    },
    {
      "date": "2024-07-02",
      "unique_id": "series1",
      "temperature": 26.5,
      "holiday": 0,
      "promotion": 1
    }
  ]
}
⚠️ Important: If a model uses exogenous variables you must provide future values for all exogenous columns across the entire forecast horizon. Missing values will cause the forecast to fail.

Best Practices

  • Use variables that are known or predictable in the future (e.g., calendar indicators).
  • Avoid variables that are highly correlated with each other to prevent multicollinearity.
  • Normalize or scale variables with very different ranges.
  • Include calendar variables (day of week, month, quarter) to capture seasonal patterns.
  • Evaluate variable impact with cross‑validation before production use.

Preprocessing Configuration

The API supports automatic outlier detection and treatment through the preprocessing_config parameter. This feature is disabled by default, so no preprocessing is applied unless you provide a configuration. Preprocessing only applies to models without exogenous variables; models with exogenous variables skip this step to preserve the integrity of external features.

Default Behavior

When preprocessing_config is omitted or set to null, no preprocessing is performed and your data is used as‑is.

Using Presets

Enable preprocessing easily by specifying a preset:

{
  "preprocessing_config": {"preset": "default"}
}

Available Presets

Preset Detection Treatment Description
default seasonal_iqr (threshold: 1.5) winsorize (5%-95%) General purpose. Applies to trailing 56 days (~8 weeks). Good for handling holiday spikes.
trailing seasonal_iqr (threshold: 2.0) seasonal_median Only clean the last 28 days. Preserves historical outliers and cleans recent anomalies that affect lag features.
aggressive iqr (threshold: 1.0) winsorize (2%-98%) Catches more outliers. Use for very noisy data with many extreme values.
conservative zscore (threshold: 3.5) clip_iqr Only removes very extreme outliers. Preserves most data points.
none none none Explicitly disable preprocessing. Same as omitting the parameter.

Custom Configuration

For fine‑grained control specify individual parameters:

{
  "preprocessing_config": {
    "outlier_detection": "seasonal_iqr",
    "outlier_treatment": "winsorize",
    "detection_threshold": 1.5,
    "winsorize_limits": [0.05, 0.95],
    "trailing_window": 56,
    "rolling_window": 7
  }
}

Custom Parameters

Parameter Type Default Description
outlier_detection string “none” Detection method (see table below).
outlier_treatment string “none” Treatment method (see table below).
detection_threshold float 1.5 Threshold for IQR or z‑score methods; higher values detect fewer outliers.
winsorize_limits [float, float] [0.05, 0.95] Lower and upper percentile bounds for winsorization.
trailing_window integer or null null Only apply preprocessing to the last N data points. null means the entire series.
rolling_window integer 7 Window size for the rolling median treatment.
Tip: You can combine a preset with custom overrides:
{"preset": "default", "detection_threshold": 2.0}

Detection Methods

MethodDescription
noneNo detection.
iqrStandard IQR method: detects values outside threshold × IQR from Q1/Q3.
zscoreZ‑score threshold: flags points more than threshold standard deviations from the mean.
seasonal_iqrIQR within same day‑of‑week groups to handle weekly seasonality.
seasonal_zscoreZ‑score within same day‑of‑week groups.
hampelHampel filter (median absolute deviation based) good for spikes.
percentileSimple percentile‑based bounds.

Treatment Methods

MethodDescription
noneNo treatment (detection only; useful for logging).
winsorizeClip outliers to percentile bounds defined by winsorize_limits.
seasonal_medianReplace outliers with the median of the same day‑of‑week.
rolling_medianReplace outliers with a rolling median computed over rolling_window.
interpolateLinearly interpolate between neighboring values.
clip_iqrClip values to IQR bounds: [Q1 − threshold×IQR, Q3 + threshold×IQR].

Error Handling

HTTP Status Codes

CodeMeaningDescription
200OKRequest succeeded and the result is returned.
202AcceptedAsynchronous job queued successfully.
400Bad RequestInvalid request parameters or data format.
401UnauthorizedMissing or invalid API key.
403ForbiddenAPI key lacks required permissions.
404Not FoundResource not found (invalid endpoint, model_id or job_id).
429Too Many RequestsRate limit exceeded – wait and retry.
500Internal Server ErrorUnexpected server error. Retry or contact support.

Error Response Format

{
  "status": "error",
  "error": "Invalid data format",
  "detail": "Column 'ds' is missing from input data",
  "code": "VALIDATION_ERROR"
}

Common Errors and Solutions

Authentication Errors
// Error
{
  "status": "error",
  "error": "API key required",
  "code": "AUTH_MISSING"
}

// Solution: Add X-API-Key header
curl -H "X-API-Key: qx_your_api_key_here" ...
Data Validation Errors
// Error
{
  "status": "error",
  "error": "Insufficient data",
  "detail": "Need at least 24 observations for horizon=12",
  "code": "DATA_LENGTH_ERROR"
}

// Solution: Provide more historical data
Rate Limit Errors
// Error: HTTP 429
{
  "status": "error",
  "error": "Rate limit exceeded",
  "retry_after": 60
}

// Solution: Wait 60 seconds before retrying

Support & Resources