Get Position History (WebSocket)
Retrieve closed position history for an authenticated subaccount over WebSocket with symbol, time-range, and pagination filters.
Endpoint
ws.send() wss://api.synthetix.io/v1/ws/tradeRequest
Request Format
{
"id": "get-position-history-1",
"method": "post",
"params": {
"action": "getPositionHistory",
"subaccountId": "123456789",
"symbol": "BTC-USDT",
"startTime": 1769364177000,
"endTime": 1769450577000,
"limit": 50,
"offset": 0,
"signature": {
"v": 27,
"r": "0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
"s": "0xbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb"
}
}
}Parameters
Request Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
id | string | Yes | Client-generated request identifier |
method | string | Yes | Must be "post" |
params | object | Yes | Request payload container |
Params Object
| Parameter | Type | Required | Description |
|---|---|---|---|
action | string | Yes | Must be "getPositionHistory" |
subaccountId | string | Yes | Subaccount ID in request payload. The authenticated selected account is enforced server-side for access control |
symbol | string | No | Filter by symbol (for example "BTC-USDT") |
startTime | integer | No | Start timestamp in milliseconds (inclusive). Cannot be more than 30 days in the past. When omitted, defaults to now − 30 days. Maximum range between startTime and endTime is 30 days. |
endTime | integer | No | End timestamp in milliseconds (inclusive). If endTime is older than 30 days and startTime is not provided, the request is rejected. Maximum range between startTime and endTime is 30 days. |
limit | integer | No | Number of records to return (default: 100, max: 1000) |
offset | integer | No | Number of records to skip (default: 0, max: 10000) |
signature | object | Yes | EIP-712 signature for the request |
This read endpoint does not require nonce management in its request flow.
Response Format
Success Response
{
"id": "get-position-history-1",
"status": 200,
"result": {
"status": "ok",
"response": {
"positions": [
{
"positionId": "2015847946616049664",
"symbol": "BTC-USDT",
"side": "long",
"entryPrice": "95000",
"quantity": "0.001",
"closePrice": "96000",
"closeReason": "close",
"leverage": 10,
"realizedPnl": "1",
"accumulatedFees": "0.1",
"netFunding": "0",
"closedAt": 1769450577774,
"createdAt": 1769450577000,
"tradeId": "123"
}
],
"hasMore": false
},
"requestId": "abcd1234",
"request_id": "abcd1234",
"timestamp": 1769450577774
}
}Error Response
{
"id": "get-position-history-1",
"status": 400,
"result": null,
"error": {
"code": "VALIDATION_ERROR",
"category": "REQUEST",
"message": "Invalid time range",
"retryable": false
}
}Position History Object
| Field | Type | Description |
|---|---|---|
positionId | string | Unique position identifier |
symbol | string | Trading pair symbol |
side | string | Position side ("long" or "short") |
entryPrice | string | Average entry price |
quantity | string | Position size |
closePrice | string | Execution price of closure |
closeReason | string | Position close reason |
leverage | integer | Position leverage at the time of close. Omitted when not set |
realizedPnl | string | Realized PnL |
accumulatedFees | string | Total fees for the position |
netFunding | string | Net funding paid/received |
closedAt | integer | Position close timestamp in milliseconds |
createdAt | integer | Position creation timestamp in milliseconds |
tradeId | string | Associated trade identifier |
EIP-712 Signature
const domain = {
name: 'Synthetix',
version: '1',
chainId: 1,
verifyingContract: '0x0000000000000000000000000000000000000000'
};
const types = {
SubAccountAction: [
{ name: 'subAccountId', type: 'uint256' },
{ name: 'action', type: 'string' },
{ name: 'expiresAfter', type: 'uint256' }
]
};
const message = {
subAccountId: '123456789',
action: 'getPositionHistory',
expiresAfter: 0
};
const signature = await signer._signTypedData(domain, types, message);Signing
All trading methods are signed using EIP-712. Each successful trading request will contain:
- A piece of structured data that includes the sender address
- A signature of the hash of that structured data, signed by the sender
For detailed information on EIP-712 signing, see EIP-712 Signing.
Error Handling
| Error Code | Description | Retryable |
|---|---|---|
UNAUTHORIZED | EIP-712 signature validation failed | No |
VALIDATION_ERROR | Request validation failed | No |
MISSING_REQUIRED_FIELD | Required field is missing | No |
INVALID_FORMAT | Field format is invalid | No |
INVALID_VALUE | Invalid parameter value | No |
RATE_LIMIT_EXCEEDED | Too many requests in time window | Yes |
INSUFFICIENT_MARGIN | Not enough margin for trade | No |
ORDER_NOT_FOUND | Order does not exist | No |
OPERATION_TIMEOUT | Operation timed out | Yes |
| Error | Description |
|---|---|
| Invalid request format | Request payload is malformed |
| Invalid subaccount | Subaccount does not exist or is not accessible |
| Invalid time range | startTime is greater than endTime |
| Time range exceeds maximum | startTime and endTime are more than 30 days apart |
| Offset exceeds maximum | offset is greater than 10000 |
| Invalid pagination | limit or offset is outside accepted bounds |
symbol is a filter field, but this endpoint does not document dedicated symbol-validation errors in its handler path.
