> ## Documentation Index
> Fetch the complete documentation index at: https://juo.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# Actions

> Available actions for schedule adjustments

Actions define what modification to apply when a schedule adjustment matches an order.

## Skip order

<Card icon="forward" horizontal>
  Prevents an order from being created. The order will be excluded from the schedule entirely.
</Card>

**Use cases:**

* Customer going on vacation
* Holiday closures
* Temporary subscription pause

**Input:**

| Field    | Type   | Required | Description                   |
| -------- | ------ | -------- | ----------------------------- |
| `reason` | string | Yes      | Reason for skipping the order |

```json theme={null}
{
  "type": "SKIP_ORDER",
  "input": {
    "reason": "Customer on vacation"
  }
}
```

***

## Change date

<Card icon="calendar" horizontal>
  Reschedules an order to a different date within the billing period.
</Card>

**Use cases:**

* Customer requests different delivery day
* Adjusting timing around events

**Input:**

| Field     | Type   | Required | Description                       |
| --------- | ------ | -------- | --------------------------------- |
| `newDate` | string | Yes      | New date for the order (ISO 8601) |

```json theme={null}
{
  "type": "CHANGE_DATE",
  "input": {
    "newDate": "2025-02-15T00:00:00Z"
  }
}
```

<Warning>
  Only supports the `CYCLE` matcher. The new date must be within one billing cycle of the original date and cannot be in the past.
</Warning>

***

## Update shipping

<Card icon="truck" horizontal>
  Updates the shipping address for a specific order.
</Card>

**Use cases:**

* Customer temporarily at different address
* One-time delivery to alternate location

**Input:**

| Field                  | Type   | Required | Description           |
| ---------------------- | ------ | -------- | --------------------- |
| `address.firstName`    | string | No       | First name            |
| `address.lastName`     | string | No       | Last name             |
| `address.address1`     | string | Yes      | Street address line 1 |
| `address.address2`     | string | No       | Street address line 2 |
| `address.city`         | string | No       | City                  |
| `address.zip`          | string | No       | Postal/ZIP code       |
| `address.countryCode`  | string | Yes      | ISO country code      |
| `address.provinceCode` | string | No       | Province/state code   |
| `address.phone`        | string | No       | Phone number          |
| `address.company`      | string | No       | Company name          |

```json theme={null}
{
  "type": "UPDATE_SHIPPING",
  "input": {
    "address": {
      "firstName": "John",
      "lastName": "Doe",
      "address1": "123 Main St",
      "city": "New York",
      "countryCode": "US",
      "zip": "10001"
    }
  }
}
```

<Warning>
  Address must include at least `address1` and `countryCode`.
</Warning>

***

## Update payment method

<Card icon="credit-card" horizontal>
  Updates the payment method for a specific order.
</Card>

**Use cases:**

* Use different card for specific order
* One-time payment method override

**Input:**

| Field             | Type   | Required | Description               |
| ----------------- | ------ | -------- | ------------------------- |
| `paymentMethodId` | string | Yes      | Payment method identifier |

```json theme={null}
{
  "type": "UPDATE_PAYMENT_METHOD",
  "input": {
    "paymentMethodId": "pm_abc123"
  }
}
```

***

## Update products

<Card icon="box" horizontal>
  Modifies product lines for a specific order.
</Card>

**Use cases:**

* One-time quantity change
* Swap variant for single order
* Adjust billing interval for specific cycle

**Input:**

| Field                              | Type    | Required | Description                                    |
| ---------------------------------- | ------- | -------- | ---------------------------------------------- |
| `lines`                            | array   | Yes      | Array of line modifications (min 1)            |
| `lines[].lineId`                   | string  | Yes      | ID of the line to modify                       |
| `lines[].variantId`                | string  | No       | New variant ID to swap to                      |
| `lines[].quantity`                 | integer | No       | New quantity (min 1)                           |
| `lines[].interval`                 | object  | No       | Override billing interval                      |
| `lines[].interval.intervalCount`   | integer | No       | Number of intervals                            |
| `lines[].interval.interval`        | string  | No       | Interval unit: DAY, WEEK, MONTH, YEAR          |
| `lines[].nextBillingDate`          | string  | No       | Override next billing date (ISO 8601)          |
| `lines[].customAttributes`         | array   | No       | Custom attributes to merge onto the order item |
| `lines[].customAttributes[].key`   | string  | Yes      | Attribute key                                  |
| `lines[].customAttributes[].value` | string  | Yes      | Attribute value                                |

```json theme={null}
{
  "type": "UPDATE_PRODUCTS",
  "input": {
    "lines": [
      {
        "lineId": "line_abc123",
        "quantity": 2
      },
      {
        "lineId": "line_def456",
        "variantId": "variant_xyz789"
      },
      {
        "lineId": "line_ghi789",
        "customAttributes": [
          { "key": "gift_message", "value": "Happy birthday!" }
        ]
      }
    ]
  }
}
```

<Info>
  Line IDs must exist in the customer's subscriptions. Attributes are merged onto the item by key — existing keys are overwritten, unspecified keys are preserved.
</Info>

<Warning>
  Reserved/internal attribute keys cannot be set via `customAttributes` and will cause the request to fail with a 400 error.
</Warning>

***

## Apply discount

<Card icon="percent" horizontal>
  Applies a discount (Shopify code or manual) to a specific order in the schedule.
</Card>

**Use cases:**

* One-time promotional discount for specific cycle
* Loyalty reward for long-term subscribers
* Compensation discount for service issues

The action supports two discount sources: Shopify discount codes and manual discounts.

### Shopify code discount

Apply an existing Shopify discount code to the order.

**Input:**

| Field            | Type   | Required | Description                        |
| ---------------- | ------ | -------- | ---------------------------------- |
| `discountSource` | string | Yes      | Must be `"code"`                   |
| `discountCode`   | string | Yes      | The Shopify discount code to apply |

```json theme={null}
{
  "type": "APPLY_DISCOUNT",
  "input": {
    "discountSource": "code",
    "discountCode": "SAVE20"
  }
}
```

<Warning>
  Discount code must exist in Shopify, be active, and apply to subscriptions. Only basic discounts and free shipping discounts are supported.
</Warning>

### Manual discount - line items

Create a custom discount targeting line items.

**Input:**

| Field            | Type   | Required | Description                                                        |
| ---------------- | ------ | -------- | ------------------------------------------------------------------ |
| `discountSource` | string | Yes      | Must be `"manual"`                                                 |
| `discountCode`   | string | Yes      | Custom discount title/name                                         |
| `discountType`   | string | Yes      | `"percentage"` or `"fixed_amount"`                                 |
| `value`          | number | Yes      | Discount value (percentage 0-100 or fixed amount in shop currency) |
| `targetType`     | string | Yes      | Must be `"line_item"`                                              |
| `targeting`      | object | Yes      | Specifies what to target                                           |

**Targeting options:**

* `{ "type": "all" }` - Apply to all line items
* `{ "type": "products", "productIds": ["gid://shopify/Product/123", ...] }` - Apply to specific products

**Example: Percentage discount on all items**

```json theme={null}
{
  "type": "APPLY_DISCOUNT",
  "input": {
    "discountSource": "manual",
    "discountCode": "Loyalty Reward",
    "discountType": "percentage",
    "value": 15,
    "targetType": "line_item",
    "targeting": {
      "type": "all"
    }
  }
}
```

**Example: Fixed amount discount on specific products**

```json theme={null}
{
  "type": "APPLY_DISCOUNT",
  "input": {
    "discountSource": "manual",
    "discountCode": "Product Promo",
    "discountType": "fixed_amount",
    "value": 10,
    "targetType": "line_item",
    "targeting": {
      "type": "products",
      "productIds": ["gid://shopify/Product/123456789"]
    }
  }
}
```

### Manual discount - shipping

Create a custom discount targeting shipping.

**Input:**

| Field            | Type   | Required | Description                   |
| ---------------- | ------ | -------- | ----------------------------- |
| `discountSource` | string | Yes      | Must be `"manual"`            |
| `discountCode`   | string | Yes      | Custom discount title/name    |
| `discountType`   | string | Yes      | Must be `"percentage"`        |
| `value`          | number | Yes      | Must be `100` (free shipping) |
| `targetType`     | string | Yes      | Must be `"shipping"`          |
| `targeting`      | object | Yes      | Must be `{ "type": "all" }`   |

**Example: Free shipping discount**

```json theme={null}
{
  "type": "APPLY_DISCOUNT",
  "input": {
    "discountSource": "manual",
    "discountCode": "Free Shipping",
    "discountType": "percentage",
    "value": 100,
    "targetType": "shipping",
    "targeting": {
      "type": "all"
    }
  }
}
```

<Warning>
  Only supports the `CYCLE` matcher. Only supports free shipping discounts (100% off) - partial shipping discounts and fixed amount shipping discounts are not supported.
</Warning>
