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

# Sign Price

> Produce an EIP-712 signed price for atomic use in a transaction

Returns an EIP-712 payload for a NAV, ready to sign. You sign it with the wallet authorized on the market's oracle, then pass the price and your signature as `signedPrice` on [Open Loan](/endpoints/lending/open-loan), [Borrow More](/endpoints/lending/borrow-more), [Withdraw Collateral](/endpoints/lending/withdraw-collateral), or [Liquidate Loan](/endpoints/lending/liquidate). The contract applies the price and the action in one transaction.

This is the alternative to [Sync Oracle Price](/endpoints/lending/sync-oracle). Signing costs no gas and writes nothing on-chain, so it suits per-transaction pricing where a borrower needs a fresh valuation without waiting for an oracle write. Pushing suits a scheduled NAV publication that every loan in the market should see.

## Path Parameters

<ParamField path="marketId" type="string" required>Market ID.</ParamField>

## Body Parameters

<ParamField body="price" type="number" required>
  Net asset value per collateral token, denominated in the market's borrow asset. Must be greater than zero.
</ParamField>

<ParamField body="validitySeconds" type="integer" default="300">
  Signature lifetime in seconds. Values below 60 are raised to 60 and values above 3600 are lowered to 3600.
</ParamField>

<ParamField body="signerAddress" type="string">
  The wallet that will sign, when price authority sits with a key this instance does not hold. Supply it and the payload is built for that address and its authorization is checked against the oracle. Omit it and the signer is resolved in order: the price signer the market's lender of record declared, then your instance's registered wallet.
</ParamField>

## Response Fields

<ResponseField name="data" type="object">
  <Expandable>
    <ResponseField name="action" type="string">Always `SIGN_TYPED_DATA`.</ResponseField>

    <ResponseField name="typedData" type="object">
      The EIP-712 payload to sign, carrying `domain`, `types`, `primaryType`, and `message`. Pass it straight to `signTypedData`.
    </ResponseField>

    <ResponseField name="display" type="object">
      The same values in readable form, also flattened onto `data` itself.
    </ResponseField>

    <ResponseField name="price" type="string">Price in base units at the borrow asset's decimals. Pass this value, not `priceUsd`, in the `signedPrice` object.</ResponseField>
    <ResponseField name="priceUsd" type="string">The same price as a human-readable decimal string. Informational.</ResponseField>
    <ResponseField name="timestamp" type="integer">Unix seconds the price is stamped at. Never ahead of chain time.</ResponseField>
    <ResponseField name="validUntil" type="integer">Unix seconds after which the signature is rejected.</ResponseField>
    <ResponseField name="signer" type="string">The wallet expected to sign. Signing with any other wallet produces a signature the oracle rejects.</ResponseField>
  </Expandable>
</ResponseField>

<Note>
  No signature is returned. You produce it by signing `typedData`. The contract then reads `price`, `timestamp`, `validUntil`, and your `signature`. Pass the first three through unchanged.
</Note>

## Signature Structure

```
domain = {
  name: "SecurityPriceOracle",
  version: "1",
  chainId: <chain the market is deployed on>,
  verifyingContract: <market oracle address>
}

PriceUpdate = {
  price:      uint256
  timestamp:  uint256
  validUntil: uint256
}
```

The signature is bound to one oracle through `verifyingContract` and expires at `validUntil`. It carries no nonce, so a signature can be replayed by anyone who holds it until it expires. Keep `validitySeconds` tight, and treat a signed price as a bearer credential over its lifetime.

Verify a signature without spending gas using [Verify Signed Price](/endpoints/lending/verify-price).

<RequestExample>
  ```bash cURL theme={null}
  curl -X POST "https://api.trusset.org/lending-external-securities/api/markets/{marketId}/sign-price" \
    -H "X-API-Key: trusset_your_key_here" \
    -H "Content-Type: application/json" \
    -d '{"price": 105.40, "validitySeconds": 300}'
  ```

  ```typescript TypeScript theme={null}
  const signRes = await fetch(
    `https://api.trusset.org/lending-external-securities/api/markets/${marketId}/sign-price`,
    {
      method: 'POST',
      headers: {
        'X-API-Key': 'trusset_your_key_here',
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({ price: 105.40, validitySeconds: 300 })
    }
  );
  const { data: signed } = await signRes.json();

  const { domain, types, message } = signed.typedData;
  const signature = await wallet._signTypedData(domain, types, message);

  const loanRes = await fetch(
    `https://api.trusset.org/lending-external-securities/api/positions/${marketId}/open-loan`,
    {
      method: 'POST',
      headers: {
        'X-API-Key': 'trusset_your_key_here',
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({
        collateralAmount: '1000',
        borrowAmount: '50000',
        signedPrice: {
          price: signed.price,
          timestamp: signed.timestamp,
          validUntil: signed.validUntil,
          signature
        }
      })
    }
  );
  ```
</RequestExample>

<ResponseExample>
  ```json Response theme={null}
  {
    "success": true,
    "data": {
      "action": "SIGN_TYPED_DATA",
      "typedData": {
        "domain": {
          "name": "SecurityPriceOracle",
          "version": "1",
          "chainId": 11155111,
          "verifyingContract": "0x8B2e...4a7c"
        },
        "types": {
          "PriceUpdate": [
            { "name": "price", "type": "uint256" },
            { "name": "timestamp", "type": "uint256" },
            { "name": "validUntil", "type": "uint256" }
          ]
        },
        "primaryType": "PriceUpdate",
        "message": {
          "price": "105400000",
          "timestamp": 1718445600,
          "validUntil": 1718445900
        }
      },
      "display": {
        "price": "105400000",
        "priceUsd": "105.4",
        "timestamp": 1718445600,
        "validUntil": 1718445900,
        "signer": "0x123...456"
      },
      "price": "105400000",
      "priceUsd": "105.4",
      "timestamp": 1718445600,
      "validUntil": 1718445900,
      "signer": "0x123...456"
    }
  }
  ```

  ```json Error - Signer Not Authorized theme={null}
  {
    "success": false,
    "error": {
      "code": "SIGNER_NOT_AUTHORIZED",
      "message": "Wallet 0x1234f9a07c6b53d81e2a4f70c9b385d6014a7e52 is not authorized on oracle 0x3b25752c1459c5cf1b0bfcfdf0d56883c8047423, and this market declared no price signer to attest for it. The oracle owner must call setAuthorizedSigner, or pass signerAddress for the key that holds price authority here.",
      "signerAddress": "0x1234f9a07c6b53d81e2a4f70c9b385d6014a7e52"
    }
  }
  ```

  ```json Error - Missing Price theme={null}
  {
    "success": false,
    "error": {
      "code": "MISSING_PRICE",
      "message": "A positive NAV price is required"
    }
  }
  ```
</ResponseExample>

## Error Codes

| Code                    | HTTP  | Cause                                                                                                                  |
| ----------------------- | ----- | ---------------------------------------------------------------------------------------------------------------------- |
| `NO_ORACLE`             | `400` | The market records no oracle address                                                                                   |
| `MISSING_PRICE`         | `400` | `price` is missing, unparseable, or not greater than zero                                                              |
| `SIGNER_NOT_AUTHORIZED` | `400` | The resolved signer is not an authorized signer on the market's oracle. The response echoes it as `signerAddress`      |
| `WALLET_NOT_CONFIGURED` | `400` | No `signerAddress` was given, the market declared no price signer, and this instance has no verified wallet registered |
| `SIGNING_FAILED`        | `400` | The payload could not be built and no more specific code applied                                                       |
| `MARKET_NOT_FOUND`      | `404` | No market with this ID on your instance                                                                                |
