API REFERENCE

Inventory Planning.

The inventory-planning endpoint turns a demand forecast into purchasing recommendations. It forecasts future demand for a single item. It then computes reorder points, safety stock, per-supplier order quantities, delivery estimates, and an overall stock-health assessment. These results tell you whether to order, how much, and from whom.

Base URL
https://forecastapi.com/v2
Authentication
Bearer YOUR_API_KEY
Generate Inventory Plan POST /v2/inventory-planning

Supply your historical demand series in data. Describe your current inventory position and suppliers in inventory_settings. The endpoint returns a full plan. It forecasts demand automatically, so you do not call /forecast separately.

Request Body

REQUEST POST /v2/inventory-planning
{
  "identifier": "SKU-12345",
  "frequency": "M",
  "periods": 6,
  "data": [
    {"date": "2024-01-31", "value": 190},
    {"date": "2024-02-29", "value": 205},
    {"date": "2024-03-31", "value": 210},
    {"date": "2024-04-30", "value": 198},
    {"date": "2024-05-31", "value": 215},
    {"date": "2024-06-30", "value": 208}
  ],
  "inventory_settings": {
    "current_stock": 300,
    "minimum_stock": 100,
    "service_level": 0.95,
    "suppliers": [
      {
        "identifier": "Acme Supply",
        "lead_time_days": 14,
        "minimum_order_quantity": 100,
        "cost_per_unit": 12.50,
        "reliability_score": 0.98
      }
    ]
  }
}

Top-level Parameters

identifier STRING · REQUIRED
Unique identifier for the item (e.g., SKU or product ID). The response echoes it.
data ARRAY · REQUIRED
This field holds the historical demand series. Each item needs a date (YYYY-MM-DD or YYYY-MM-DD HH:MM:SS, consistent across the series) and a numeric value.
periods INTEGER · REQUIRED
Number of future periods to forecast (min 1). It must cover at least the longest supplier lead time.
frequency STRING · REQUIRED
Series granularity: H, D, W, M, MS, ME, Q, or Y. The endpoint uses it to convert supplier lead times (in days) into forecast periods.
inventory_settings OBJECT · REQUIRED
Inventory position and supplier configuration. See the two tables below.
start_date DATE · OPTIONAL
Anchor date for the forecast and for all returned dates (delivery, next order). It defaults to the last date in data.
data_type STRING · DEFAULT inventory
Semantic type for model selection. This endpoint defaults it to "inventory", which enables intermittent-demand methods.
model STRING · DEFAULT standard
Forecasting model behind the plan: standard (default), advanced-quantized, advanced-patched, or auto. auto routes each identifier to the model that proved most accurate on that series. It uses the same evidence that /forecast and /batch accumulate. On this endpoint the auto ensemble default runs as standard until a winning model emerges. See Model Options. Advanced variants and auto cost 25% more usage.
selection_metric STRING · DEFAULT auto
Back-testing metric that picks the winning model: auto (default), combined, mase, or smape. It has the same semantics as on /forecast.
confidence_level FLOAT · DEFAULT 0.80
Confidence level for the forecast intervals that drive safety-stock variability (0.10–0.99). Default: 0.80.
tenant_context STRING · OPTIONAL
Optional multi-tenant scoping tag. The response echoes it.

inventory_settings Object

current_stock NUMBER ≥ 0 · REQUIRED
Units currently on hand. It drives stock status, days of coverage, and order quantities.
minimum_stock NUMBER ≥ 0 · REQUIRED
The minimum level you never want stock to fall below. The endpoint reserves it from available stock and adds it to the reorder point.
service_level NUMBER 0.5–0.999 · REQUIRED
Target probability of no stockout during lead time. The endpoint maps it to a Z-score that scales safety stock (e.g. 0.95 → 1.65, 0.99 → 2.33). A higher value means more buffer.
suppliers ARRAY (MIN 1) · REQUIRED
One or more suppliers to evaluate. The endpoint produces a recommendation for each supplier. It treats the lowest total cost as the "best" supplier, which drives the top-level plan. See the table below.
scheduled_receipts ARRAY · OPTIONAL
Purchase or production orders already placed but not yet received or finished, dated by expected arrival (not order date). A receipt that arrives before a candidate order could be delivered counts as available supply and reduces that supplier's order_quantity. All receipts feed the stock projection. See the item shape below.
committed_outflows ARRAY · OPTIONAL
Firm outgoing commitments (booked sales orders, reservations), dated by expected ship date. The endpoint treats them as allocations against stock, in addition to the forecast. Provide commitments that the forecast does not already predict. Commitments above available stock increase the suggested order by the backlog. See the item shape below.

scheduled_receipts[] / committed_outflows[] Object

date DATE · REQUIRED
Expected arrival date (receipts) or expected outgoing date (outflows), YYYY-MM-DD. The endpoint treats any past date as an immediate arrival.
quantity NUMBER ≥ 0 · REQUIRED
Number of units. The endpoint accepts value as an alias, which matches the shape of data items. You can send committed outgoing items exactly like forecast data points.
How scheduled flows change the plan
When either array is present, stock_analysis gains a per-period projected_stock timeline. The endpoint then computes days_of_coverage, next_order_date and stockout_risk from that projection. It no longer assumes a flat daily demand rate. A delivery on the 10th changes the projection on the 10th. A shipment of 100 pieces on the 15th changes it on the 15th. Requests without these fields behave exactly as before.

suppliers[] Object

identifier STRING · REQUIRED
Supplier name or ID. The response returns it as supplier in each recommendation.
lead_time_days NUMBER ≥ 0.1 · REQUIRED
Delivery lead time in days. The endpoint converts it to whole forecast periods (rounded up, min 1) to compute lead-time demand and the expected delivery date.
minimum_order_quantity NUMBER ≥ 0 · REQUIRED
MOQ. The endpoint rounds any suggested order to the next whole multiple of this value.
cost_per_unit NUMBER ≥ 0 · REQUIRED
Unit cost. It drives total order cost and the "best supplier" selection (lowest total cost wins).
reliability_score NUMBER 0.1–1.0 · DEFAULT 1.0
How dependable the supplier is. The endpoint scales safety stock by 1 / reliability_score, so a less reliable supplier gets a larger buffer. It defaults to 1.0 when omitted.

Response

RESPONSE 200 OK
{
  "result": {
    "tenant_context": null,
    "identifier": "SKU-12345",
    "current_stock": 300,
    "minimum_stock": 100,
    "reorder_point": 377.35,
    "safety_stock": 67.35,
    "suppliers": [
      {
        "supplier": "Acme Supply",
        "order_quantity": 200,
        "total_cost": 2500.00,
        "cost_per_unit": 12.5,
        "expected_delivery": "2024-07-14",
        "lead_time_days": 14,
        "minimum_order_quantity": 100,
        "reliability_score": 0.98,
        "lead_time_demand": 210.00,
        "safety_stock": 67.35,
        "reorder_point": 377.35,
        "reason": "$12.50 per unit, reasonable lead time, high reliability"
      }
    ],
    "stock_analysis": {
      "days_of_coverage": 29,
      "stockout_risk": 0.75,
      "next_order_date": "2024-06-30",
      "daily_demand_rate": 7.06,
      "stock_status": "reorder_needed"
    },
    "forecasts": [
      {"period": 1, "date": "2024-07-31", "forecast": 210.00, "lower": 180.00, "upper": 250.00},
      {"period": 2, "date": "2024-08-31", "forecast": 205.00, "lower": 175.00, "upper": 245.00}
    ]
  },
  "meta": {
    "timing": { "validation": 3.2, "planning": 284.1, "total": 288.5 }
  }
}

The response always has this single shape on success (HTTP 200): a result object with the plan and a meta object with timing. There are no alternate success response types.

result Fields

identifier STRING
The item identifier. The response echoes it from the request.
tenant_context STRING | NULL
The tenant tag. The response echoes it from the request (null if you did not send it).
current_stock NUMBER
Current on-hand units. The response echoes them from the request.
minimum_stock NUMBER
The minimum stock floor. The response echoes it from the request.
reorder_point NUMBER
The stock level at which to reorder, from the best (cheapest) supplier. It equals lead_time_demand + safety_stock + minimum_stock. The value is 0 if the endpoint could evaluate no supplier.
safety_stock NUMBER
Buffer stock from the best supplier, sized from forecast uncertainty, service level, and supplier reliability.
suppliers ARRAY
One recommendation object per input supplier (see below).
stock_analysis OBJECT
Overall stock-health summary, including stock_status (see below).
forecasts ARRAY
The underlying demand forecast used to build the plan (see below).

suppliers[] Fields

supplier STRING
Supplier identifier from the request.
order_quantity NUMBER
Recommended units to order, rounded to the next multiple of the MOQ. 0 means you need no order right now.
total_cost NUMBER
order_quantity × cost_per_unit, rounded to 2 decimals.
cost_per_unit NUMBER
Unit cost. The response echoes it from the request.
expected_delivery DATE
start_date + lead_time_days, formatted YYYY-MM-DD.
lead_time_days NUMBER
Lead time. The response echoes it from the request.
minimum_order_quantity NUMBER
MOQ. The response echoes it from the request.
reliability_score NUMBER
Reliability. The response echoes it from the request (or 1.0 if you omitted it).
lead_time_demand NUMBER
Forecast demand summed over the lead-time periods.
safety_stock NUMBER
Buffer for this supplier: demand_variability × Z(service_level) × (1 / reliability_score).
reorder_point NUMBER
lead_time_demand + safety_stock + minimum_stock for this supplier.
reason STRING
Human-readable rationale for the recommendation (see values below).
incoming_within_lead_time NUMBER
Scheduled receipts that arrive on or before this supplier's expected_delivery. The endpoint counts them as available supply when it sizes the order. This field is present only when the request included scheduled flows.
committed_within_lead_time NUMBER
Committed outflows dated on or before this supplier's expected_delivery. The endpoint allocates them against stock when it sizes the order. This field is present only when the request included scheduled flows.

stock_analysis Fields

days_of_coverage INTEGER
How many days the available stock (above the minimum) lasts at the average daily demand rate. The value is 999 when there is no forecast demand. With scheduled flows, the endpoint reads it from the stock projection instead.
stockout_risk NUMBER
Estimated probability of a stockout (0–1). The endpoint returns one of a fixed set of values (see below). With scheduled flows, near-term committed outflows count as demand and near-term receipts count as supply.
next_order_date DATE
Estimated date the stock will fall to the reorder point. It equals start_date when you are already at or below it (order now). With scheduled flows, the endpoint reads it from the stock projection.
daily_demand_rate NUMBER
Average forecast demand per day across all forecast periods.
stock_status STRING
A single label for stock health. It has one of four values (see below). With scheduled flows, the endpoint assesses it on the inventory position (on hand + all scheduled receipts − all committed outflows) instead of raw current_stock.
projected_stock ARRAY
Per-period stock projection: each entry has date, scheduled_receipts, forecast_demand, committed_outflow, and a running projected_stock. Negative values signal a projected shortage. This field is present only when the request included scheduled flows.

stock_status — possible values

The status compares your current_stock against the best supplier's reorder_point and your minimum_stock. The endpoint checks the rows in order, so the first matching row wins.

Value Condition Meaning
critical current_stock ≤ minimum_stock At or below the minimum floor. This is the highest urgency, because you have no usable buffer left.
reorder_needed minimum_stock < current_stock ≤ reorder_point Below the reorder point. Place an order now to avoid a future stockout during lead time.
low reorder_point < current_stock ≤ reorder_point × 1.2 Within 20% above the reorder point. This is not urgent, but watch it, because a reorder is near.
adequate current_stock > reorder_point × 1.2 Healthy. Stock sits well above the reorder point. You need no action.
Edge case
If the endpoint could evaluate no supplier, the best-supplier reorder_point is 0. Then any positive stock above the minimum reports as adequate. In normal requests (at least one supplier) this does not happen.

stockout_risk — possible values

This is a coarse risk estimate rather than a continuous probability. Let stock_ratio = (current_stock − minimum_stock) / demand over the next 3 periods. The endpoint returns exactly one of these values:

Value Returned when
0.99 current_stock ≤ minimum_stock (at or below the floor).
0.01 Near-term demand is zero, or stock_ratio ≥ 2.0.
0.05 1.5 ≤ stock_ratio < 2.0.
0.15 1.0 ≤ stock_ratio < 1.5.
0.35 0.5 ≤ stock_ratio < 1.0.
0.75 stock_ratio < 0.5.

reason — how it is built

When you need no order, reason is exactly "No order needed - current stock is sufficient". Otherwise it is a comma-separated string. The endpoint builds it from the fragments below and skips empty fragments. If none apply, it uses "standard recommendation" instead.

Fragment Included when
"$X.XX per unit" cost_per_unit > 0.
"fast delivery" / "reasonable lead time" / "longer lead time" Lead time ≤ 7 days / ≤ 14 days / otherwise.
"high reliability" / "good reliability" Reliability ≥ 0.95 / ≥ 0.85 (below 0.85 adds nothing).
"minimum order quantity" The recommended order equals the MOQ exactly.

forecasts[] Fields

The demand forecast that the plan uses. Fields depend slightly on the selected model. Every entry always includes a point forecast and an upper bound. These two values drive lead-time demand and safety stock.

period INTEGER
1-based index of the forecast period.
date STRING
Period date (YYYY-MM-DD, or YYYY-MM-DD HH:00:00 for hourly data).
forecast NUMBER
Point demand forecast for the period (never negative).
lower NUMBER
Lower bound of the confidence interval.
upper NUMBER
Upper bound of the confidence interval. Its gap above forecast is the demand variability used for safety stock.

meta.timing

Server-side timing in milliseconds: validation (request checks), planning (forecast + inventory math), and total (whole request).

Acting on the Recommendations

There is no single action field. Three fields together express the recommended action: stock_analysis.stock_status (how urgent), each supplier's order_quantity (how much, and from whom), and reason (why). The table below maps the status to your action.

stock_status Recommended action
critical Order immediately, and consider expediting. Pick the supplier with a non-zero order_quantity and the earliest expected_delivery — cost is secondary when you are below the floor.
reorder_needed Place an order this cycle. The top-level reorder_point and safety_stock come from the cheapest supplier. Use its order_quantity unless lead time or reliability pushes you to another entry.
low You need no immediate order, but a reorder is near. Watch next_order_date and days_of_coverage. Batch this into your next purchase run.
adequate Do nothing. Stock sits well above the reorder point. order_quantity will typically be 0 for every supplier.
Usage & Cost
Each call counts as one standard API call. An advanced model consumes 25% more usage, exactly as on the forecast endpoint. The same rate limits apply.

Error Responses

HTTP Status Codes

401
Unauthorized — Invalid or missing API key.
422
Unprocessable Entity — Validation failed — e.g. missing inventory_settings fields, an empty suppliers array, a bad date format, or too many data points for your plan. The body lists per-field errors.
429
Too Many Requests — Rate limit exceeded.
500
Internal Server Error — The forecast or planning step failed (e.g. the endpoint could produce no usable forecast). The response returns a generic error body.

422 Validation Error

{
  "message": "The inventory_settings.suppliers field is required.",
  "errors": {
    "inventory_settings.suppliers": [
      "The inventory_settings.suppliers field is required."
    ]
  }
}

500 Planning Error

{
  "error": "Inventory planning failed",
  "time_taken_ms": 42.7
}

Next Steps

LAST UPDATED — 30 AUG 2026 · FORECASTAPI DOCS
WAS THIS USEFUL? YES NO