# Trigger orders

Zeta supports trigger orders which can be permissionlessly executed based on a set condition - either a price or a timestamp. You'll see these as "Take-profit/Stop-loss" on dex.zeta.markets, but you can make more complicated triggers yourself in the SDK too.

### The TriggerOrder account

When a trigger order is placed using the `place_trigger_order` instruction, a new `TriggerOrder` account is created. This account contains all necessary information about the order, and is deleted when the order is executed.&#x20;

<figure><img src="/files/CPDHx5kTSPdgxMTvYztf" alt=""><figcaption><p>The TriggerOrder account on chain</p></figcaption></figure>

The relevant `TriggerOrder` accounts for a given `CrossMarginAccount` can be found by checking the `trigger_order_bits` of the `CrossMarginAccount`. If a bit is 1, then the corresponding `TriggerOrder` account exists (see `utils.getTriggerOrder()` to see how the seeds work). One account can hold up to 128 triggers, as the bits value stored is a u128.

### What can you do with triggers?

Besides regular TP/SL, trigger orders allow you to set any price+direction or timestamp as the trigger. Just be careful with margining, as **margin requirements are not checked at the time you place a trigger, but only when it executes!** Think of it as simply placing an order in the future.

You can do anything that a regular PlaceOrder allows you to do, including different order types, reduceOnly and setting your own order price.

You can also edit trigger orders before they execute using the `edit_trigger_order` instruction.

### Executing a trigger

When either the price trigger or timestamp trigger is valid, a trigger order can be executed by calling the `execute_trigger_order` instruction. This is permissionless, so anyone can execute anyone's trigger orders! If the condition has not been met yet, a `TriggerOrderCannotBeExecuted` error will be returned.

As mentioned earlier, margin requirements are only checked when the trigger order executes. This is generally not an issue for the standard TP/SL offered on dex.zeta.markets as reduceOnly is set to true, but you might want to be careful if you're making your own triggers that increase your position.

TP/SL on dex.zeta.markets uses a FillOrKill order type for market, and Limit order type for limit, and sets order\_price to be 5% away from trigger\_price by default (you can edit this slippage in the Settings page). Therefore the slippage should be enough to cross the spread in volatile conditions.

### Trigger admin

There is extra control given to the `State.trigger_admin` account, which is set to our crank's wallet. This account has the power to delete active trigger orders, which it does in certain conditions:

* If a trigger order fails too many times (currently 300, which corresponds to approx 50 mins of failed execution)
* If a TP/SL trigger is left hanging after a user closes their position, to ensure frontend UX remains fluid.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.zeta.markets/zeta-protocol/exchange-architecture/trigger-orders.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
