---
title: "Get an experiment's results"
method: GET
path: "/api/v1/experiments/{id}/results"
tags: ["Experiments"]
---

# Get an experiment's results

`GET /api/v1/experiments/{id}/results`

## Request

- Base URL: `https://mailinapp.com`
- URL: `https://mailinapp.com/api/v1/experiments/{id}/results`
- Auth: HTTP bearer

The experiment plus its full report, the same as the dashboard's JSON export.

## Path parameters

- `id` string, required

## Response `200`

The experiment and its report

- object
  - `experiment` Experiment, required: An A/B experiment. A send experiment mails its arms; a journey experiment's arms are a journey split's paths, and contacts are assigned as they reach the split. The same object is the `experiment` in the experiment.decided and experiment.completed webhook events.
    - `id` string, required
    - `name` string, required
    - `kind` 'send' | 'journey', required
    - `status` 'draft' | 'scheduled' | 'sending' | 'observing' | 'analyzing' | 'decided' | 'inconclusive' | 'closed' | 'cancelled', required
    - `projectId` string, required: The email the experiment is stored on: the one it sends, or for a journey experiment the first email its split reaches.
    - `journey` object, nullable, required: Null for a send experiment.
      - `journeyId` string, required
      - `nodeId` string, required: The split step.
      - `windowHours` integer, required: How long each contact is measured from reaching the split.
    - `hypothesis` string, required
    - `primaryMetric` 'purchase_conversion' | 'revenue_per_delivered' | 'unique_click_rate' | 'response_rate' | 'reveal_rate' | 'post_reveal_click_rate' | 'open_rate' | 'goal_rate' | 'unsubscribe_rate' | 'complaint_rate', required: `goal_rate` is for journey experiments only.
    - `secondaryMetrics` ExperimentMetric[], required
    - `guardrailMetrics` ExperimentMetric[], required
    - `analysis` 'fixed' | 'sequential', required
    - `arms` ExperimentArm[], required
      - `key` string, required
      - `label` string, required
      - `isControl` boolean, required
      - `isHoldout` boolean, required: A holdout is mailed nothing.
      - `allocation` number, required: The arm's share of the sample, 0–1.
      - `pathIndex` integer, nullable, required: The split path this arm is (0-based), for a journey experiment; null for a send experiment.
    - `createdAt` integer, required: Epoch milliseconds, like every time below.
    - `lockedAt` integer, nullable, required
    - `sendAt` integer, required
    - `observationEndsAt` integer, nullable, required
    - `closedAt` integer, nullable, required
    - `result` object, nullable, required: What the statistics engine said in the latest analysis; null before the first.
      - `outcome` 'invalid' | 'winner' | 'no_difference' | 'inconclusive', required
      - `armKey` string, nullable, required: The winning arm, for a winner.
      - `final` boolean, required: The analysis covers the whole observation window.
      - `computedAt` integer, required
    - `decision` object, nullable, required: What a person recorded; null until then.
      - `outcome` 'winner' | 'inconclusive' | 'no_difference', required
      - `armKey` string, nullable, required
      - `pathIndex` integer, nullable, required: For a journey experiment's winner, the path everyone can be sent down. Sending them is done by a person in the journey editor, never automatically.
      - `evidence` 'significant' | 'not_significant' | 'invalid', required: What the statistics said when the decision was recorded.
      - `rationale` string, required
      - `decidedAt` integer, required
    - `deployment` union, required: How the winner was put to use; null until then. A path deployment has no email.
      - object
        - `kind` 'email', required
        - `projectId` string, required: The email made from the winning arm.
        - `armKey` string, required
        - `deployedAt` integer, required
      - object
        - `kind` 'path', required
        - `pathIndex` integer, required
        - `armKey` string, required
        - `deployedAt` integer, required
    - `resultsUrl` string, uri, required: The results page in the dashboard.
  - `report` ExperimentReport, required: The dashboard's report export (aggregates only, never a contact): pre-registration, sample design, delivery, the latest analysis snapshot with each arm's metrics, intervals and quality checks, the daily history and the decision. Fields not listed here may be added.
    - `experiment` object, required
    - `preRegistration` object, required
    - `arms` object[], required
    - `rewards` object, nullable: Per-arm reward codes issued and failed; null without a rewarded arm or before the send.
      - `arms` object[]
        - `key` string
        - `issued` integer
        - `failed` integer
    - `money` object, nullable: Attributed revenue, AOV, promotional cost, refunds and code redemption per arm per currency; null before an analysis that has them.
      - `currency` string, nullable: The experiment's currency; other currencies are listed apart and never added in.
      - `note` string: Revenue excludes taxes and shipping; discounts are already reflected; not a profit calculation.
      - `arms` object[]: One entry per arm per currency with orders (the experiment's currency always).
        - `armKey` string
        - `currency` string
        - `denominator` integer: Delivered recipients (assigned for the holdout) that revenue per delivered divides by.
        - `purchasers` integer: Recipients with at least one attributed order in the window.
        - `orders` integer: Attributed orders in the window.
        - `grossRevenue` number: Merchandise after discounts, without taxes and shipping, before refunds.
        - `refunds` number: Merchandise refunded in the window, subtracted from revenue.
        - `refundedOrders` integer: Orders with a refund in the window.
        - `revenue` number: grossRevenue minus refunds.
        - `aov` number, nullable: Average order value: grossRevenue / orders.
        - `revenuePerDelivered` number, nullable: revenue / denominator.
        - `discount` number: The orders' discount-code amounts on the goods.
        - `freeShippingOrders` integer: Orders that used a free-shipping code.
        - `shippingSubsidy` number, nullable: The arm reward's configured shipping subsidy estimate per order.
        - `promoCost` number: Promotional cost granted: discount + shippingSubsidy × freeShippingOrders.
      - `redemption` object[]: Per rewarded arm, codes redeemed on an attributed order over codes issued.
        - `armKey` string
        - `issued` integer
        - `redeemed` integer
        - `rate` number, nullable: redeemed / issued; null when none were issued.
    - `results` object, nullable, required: The latest analysis snapshot; null before the first.
      - `orders` object: Attributed orders in the window by attribution rule (discount_code, utm, checkout_token, email_match; email_match is probable) and those left out.
        - `byRule` object
        - `excluded` object
          - `otherCurrency` integer
      - `money` object: The same money summary as the top-level money, without currency and note.
    - `history` object[], required
    - `decision` object, nullable, required
    - `journey` object, nullable, required: A journey experiment's design and enrollment; null for a send experiment.
      - `journeyId` string, required
      - `deleted` boolean, required: The journey was deleted after the experiment ended; its results stay.
      - `nodeId` string, required
      - `windowHours` integer, required
      - `enrollmentEndsAt` integer, nullable, required
      - `maturing` integer, required: Assigned contacts still inside their window, not yet counted.
      - `assignedByDay` object[], required
        - `day` string
        - `arms` object
      - `edits` object[], required: Changes to the paths' steps saved while the experiment observed, oldest first.
    - `concurrentExperiments` object[], required: Other experiments the quality checks tested this one against for an interaction.
      - `id` string, required
      - `name` string, nullable, required
      - `projectId` string, nullable, required
      - `journeyId` string, nullable, required
    - `generatedAt` integer, required

## Other responses

- `401`: Missing or invalid API key
- `404`: Not found, or not this account's
- `429`: Too many requests for this key

---

[API](https://skmtc.dev/mailinapp/apis/mailinapp-api.md) · [All operations](https://skmtc.dev/mailinapp/apis/mailinapp-api/llms.txt) · [OpenAPI document](https://skmtc.dev/mailinapp/apis/mailinapp-api/revisions/61016f797884?raw)
