TradingPosition#
tradeexecutor.state.position.TradingPosition Python class in Trading Strategy framework.
- class TradingPosition[source]#
Bases:
GenericPosition
Represents a single trading position.
Each position trades a single asset
Position is opened when the first trade is made
Position is closed when the last remaining quantity is sold/closed
Position can have its target trigger levels for
take_profit
andstop_loss
Position can have multiple trades and increase or decrease the position exposure
Positions are revalued outside the trades
Trades for the position can have different triggers: rebalance, stop los, etc.
Position can be marked as frozen meaning the automatic system does not how to clean it up
- __init__(position_id, pair, opened_at, last_pricing_at, last_token_price, last_reserve_price, reserve_currency, trades=<factory>, closed_at=None, frozen_at=None, unfrozen_at=None, last_trade_at=None, portfolio_value_at_open=None, stop_loss=None, take_profit=None, trailing_stop_loss_pct=None, notes=None, balance_updates=<factory>, trigger_updates=<factory>)#
- Parameters:
position_id (int) –
pair (TradingPairIdentifier) –
opened_at (datetime) –
last_pricing_at (datetime) –
last_token_price (float) –
last_reserve_price (float) –
reserve_currency (AssetIdentifier) –
trades (Dict[int, TradeExecution]) –
balance_updates (Dict[int, BalanceUpdate]) –
trigger_updates (List[TriggerPriceUpdate]) –
- Return type:
None
Methods
__init__
(position_id, pair, opened_at, ...)add_balance_update_event
(event)Include a new balance update event
add_notes_message
(msg)Add a new message to the notes field.
calculate_quantity_usd_value
(quantity)Calculate value of asset amount using the latest known price.
calculate_value_using_price
(token_price, ...)Calculate the value of this position using the given prices.
can_be_closed
([epsilon])There are no tied tokens in this position.
from_dict
(kvs, *[, infer_missing])from_json
(s, *[, parse_float, parse_int, ...])Get token quantity still availble for the trades in this strategy cycle.
Calculate average buy price.
The average price paid for all assets on the long or short side.
Calculate average buy price.
Iterate over all balance update events.
Get quantity of all balance udpdates for this position.
How many units we have bought total
Get the total value of the position when it was bought.
Calculate how much portfolio capital was risk when this position was opened.
Get the price when the position was closed.
Get the price of the base asset based on the latest valuation.
How long this position was held.
How many asset units this position tolds.
get_executed_trades
()Get all trades that have failed in the execution.
Get the first trade for this position.
Return the revert reason why this position is frozen.
How to refer this position in log output.
One trading pair may have multiple open positions at the same time.
Get the the last trade for this position.
Get the latest transaction performed for this position.
What is the maximum risk of this position.
What is the maximum risk of this position.
Get the largest size of this position over the time
get_name
()Get human readable name for this position
The difference in the quantity of assets bought and sold to date.
Get the price when the position was opened.
Get the original stop loss value when this position was opened.
Get the price of the position at open.
Get the tied up token quantity in all successfully executed trades.
Get the quanaity of the asset the position at open.
Get the unit name we label the quantity in this position
Calculated life-time profit over this position.
Calculates the profit & loss (P&L) that has been 'realised' via two opposing asset transactions in the Position to date.
How many units we have sold total
Get the total value of the position when it was sold.
Calculated life-time profit over this position.
Get all trades that have been successfully executed and contribute to this position
How much money we have used on buys
Get the total amount of swap fees paid in the position.
get_total_profit_at_timestamp
(timestamp)Get the profit of the position what it was at a certain point of time.
How much % we have made profit so far.
Realised + unrealised profit.
How much money we have received on sells
Get the number of trades in this position.
get_trades_by_strategy_cycle
(timestamp)Get all trades made for this position at a specific time.
Get the reserve currency allocated for trades.
Calculate the position unrealised profit.
Get the position value using the latest revaluation pricing.
How much the position had value tied after its close.
How much the position had value tied after its open.
This position has stop loss/take profit set.
Do we have legacy / incompatible data issues.
has_buys
()Does is position have any spot buys.
This position represents actual holdings and has executed trades on it.
has_planned_trades
()Does is position have any spot sells.
has_trade
(trade)Check if a trade belongs to this position.
Does this position need to check for stop loss/take profit.
has_unexecuted_trades
()This position has been closed and does not have any capital tied to it.
This position has had a failed trade and can no longer be automatically moved around.
is_long
()Is this position long on the underlying base asset.
is_loss
()This position is currently having non-zero losses.
is_open
()This is an open trading position.
This position is currently having non-zero profit.
This position was frozen, but its trades were successfully repaired.
is_short
()Is this position short on the underlying base asset.
Was this position ended with stop loss trade
Did this position close with stop loss.
Was this position ended with take profit trade
Did this position close with trake profit.
Was this position ended with a trailing stop loss trade.
This position was frozen, but its trades were successfully repaired.
open_trade
(strategy_cycle_at, trade_id, ...)Open a new trade on position.
schema
(*[, infer_missing, only, exclude, ...])set_revaluation_data
(last_pricing_at, ...)to_dict
([encode_json])to_json
(*[, skipkeys, ensure_ascii, ...])Attributes
Runnint int counter primary key for positions
Trading pair this position is trading
When this position was opened
When was the last time this position was (re)valued
Last valued price for the base token.
last_reserve_price
Which reserve currency we are going to receive when we sell the asset
List of trades taken for this position.
When this position was closed
Timestamp when this position was moved to a frozen state.
Timestamp when this position was marked lively again
When this position had a trade last time
Record the portfolio value when the position was opened.
Trigger a stop loss if this price is reached,
Trigger a take profit if this price is reached
Trailing stop loss.
Human readable notes about this trade
All balance updates that have touched this reserve position.
Trigger updates are stored oldest first.
- pair: TradingPairIdentifier#
Trading pair this position is trading
- last_token_price: float#
Last valued price for the base token.
There are two ways to receive this
When the position is opened, set to the initial buy price
When the position is revalued, set to the sell price of the position
Note that this might be initially incorrect, if revaluation has not been done yet, because the buy price != sell price.
- reserve_currency: AssetIdentifier#
Which reserve currency we are going to receive when we sell the asset
- trades: Dict[int, TradeExecution]#
List of trades taken for this position. trade_id -> Trade map
- frozen_at: Optional[datetime]#
Timestamp when this position was moved to a frozen state.
This can happen multiple times, so is is the last time when this happened.
See also
unfrozen_at
.
- unfrozen_at: Optional[datetime]#
Timestamp when this position was marked lively again
Set by
tradeexecutor.state.repair
when the position trades are repaired and the position is moved to open or closed list.
- portfolio_value_at_open: Optional[float]#
Record the portfolio value when the position was opened.
This can be later used to analyse the risk of the trades. (“Max value at the risk”)
- stop_loss: Optional[float]#
Trigger a stop loss if this price is reached,
We use mid-price as the trigger price.
- take_profit: Optional[float]#
Trigger a take profit if this price is reached
We use mid-price as the trigger price.
- trailing_stop_loss_pct: Optional[float]#
Trailing stop loss.
For details see Trailing stop loss.
Set the trailing stop as the percentage of the market price. This will update
stop_loss
price if the new resultingstop_loss
will be higher as the previous one.Percents as the relative to the the market price, e.g. for 10% trailing stop loss set this value for 0.9.
Calculated as stop_loss = mid_price trailing_stop_loss_pct.
Updated by
tradeexecutor.strategy.stop_loss.check_position_triggers()
. For any updates you can readtrigger_updates
.
- notes: Optional[str]#
Human readable notes about this trade
Special case; not worth to display unless the field is filled in.
May contain multiple newline separated messages
Used to mark test trades from command line.
Used to add log information abotu frozen and unfrozen positions
- balance_updates: Dict[int, BalanceUpdate]#
All balance updates that have touched this reserve position.
Generated by
tradeexecutor.strategy.sync_model.SyncModel
.BalanceUpdate.id -> BalanceUpdate mapping
- trigger_updates: List[TriggerPriceUpdate]#
Trigger updates are stored oldest first.
- is_closed()[source]#
This position has been closed and does not have any capital tied to it.
- Return type:
- is_frozen()[source]#
This position has had a failed trade and can no longer be automatically moved around.
After the position is unfrozen the flag goes away.
- Return type:
- is_unfrozen()[source]#
This position was frozen, but its trades were successfully repaired.
- Return type:
- is_repaired()[source]#
This position was frozen, but its trades were successfully repaired.
Alias for
is_unfrozen()
.- Return type:
- get_first_trade()[source]#
Get the first trade for this position.
Considers unexecuted trades.
- Return type:
- get_last_trade()[source]#
Get the the last trade for this position.
Considers unexecuted and failed trades.
- Return type:
- is_long()[source]#
Is this position long on the underlying base asset.
We consider the position long if the first trade is buy.
- Return type:
- is_trailing_stop_loss()[source]#
Was this position ended with a trailing stop loss trade.
Position was terminated with a stop loss
Trailing stop loss was set
Trailing stop loss was updated at least once
- Return type:
- has_executed_trades()[source]#
This position represents actual holdings and has executed trades on it.
This will return false for positions that are still planned or have zero successful trades.
- Return type:
- has_trigger_conditions()[source]#
Does this position need to check for stop loss/take profit.
- Return type:
- get_quantity_unit_name()[source]#
Get the unit name we label the quantity in this position
- Return type:
- get_balance_update_events()[source]#
Iterate over all balance update events.
Balance updates describe external events affecting the balance of this position: the update was not triggered by the trade executor itself.
Deposits
Redemptions
Account corrections
Trades are not included here
- Return type:
- get_balance_update_quantity()[source]#
Get quantity of all balance udpdates for this position.
- Returns:
How much in-kind redemption events have affected this position.
Decimal zero epsilon noted.
- Return type:
- get_quantity()[source]#
Get the tied up token quantity in all successfully executed trades.
Does not account for trades that are currently being executed.
Does some fixing for rounding errors in the form of epsilon checks
Accounts for any balance update events (redemptions, interest, accounting corrections)
- Returns:
Number of asset units held by this position.
Rounded down to zero if the sum of
- Return type:
- get_available_trading_quantity()[source]#
Get token quantity still availble for the trades in this strategy cycle.
This includes
All executed trades
All planned trades for this cycle that have already reduced/increased amounts for this position
This gives you remaining token balance, even if there are some earlier sell orders that have not been executed yet.
- Return type:
- get_current_price()[source]#
Get the price of the base asset based on the latest valuation.
- Return type:
- get_equity_for_position()[source]#
How many asset units this position tolds.
TODO: Remove this
Alias for
get_quantity()
- Return type:
- get_identifier()[source]#
One trading pair may have multiple open positions at the same time.
- Return type:
- get_successful_trades()[source]#
Get all trades that have been successfully executed and contribute to this position
- Return type:
- calculate_value_using_price(token_price, reserve_price)[source]#
Calculate the value of this position using the given prices.
- get_value()[source]#
Get the position value using the latest revaluation pricing.
If the position is closed, the value should be zero.
- Return type:
- get_trades_by_strategy_cycle(timestamp)[source]#
Get all trades made for this position at a specific time.
- Returns:
Iterable of 0….N trades
- Parameters:
timestamp (datetime) –
- Return type:
- get_unexeuted_reserve()[source]#
Get the reserve currency allocated for trades.
Assumes position can only have one reserve currency.
Only spot buys can have unexecuted reserve.
- Returns:
Amount of capital we have allocated in trades that did not correctly execute
- Return type:
- open_trade(strategy_cycle_at, trade_id, quantity, reserve, assumed_price, trade_type, reserve_currency, reserve_currency_price, pair_fee=None, lp_fees_estimated=None, planned_mid_price=None, price_structure=None, slippage_tolerance=None)[source]#
Open a new trade on position.
Trade can be opened by knowing how much you want to buy (quantity) or how much cash you have to buy (reserve).
- Parameters:
strategy_cycle_at (datetime.datetime | None) –
The strategy cycle timestamp for which this trade was executed.
Might not be available for the accounting corrections done offline.
trade_id (int) – Trade id allocated by the portfolio
quantity (Optional[Decimal]) –
How many units this trade does.
Positive for buys, negative for sells in the spot market.
assumed_price (float) –
The planned execution price.
This is the price we expect to pay per quantity unit after the execution. This is the mid price + any LP fees included.
trade_type (TradeType) – What kind of a trade is this.
reserve_currency (AssetIdentifier) –
Which portfolio reserve we use for this trade.
- param reserve_currency_price:
If the quote token is not USD, then the exchange rate between USD and quote token we assume we have.
Actual exchange rate may depend on the execution.
pair_fee (Optional[float]) – The fee tier from the trading pair / overriden fee.
lp_fees_estimated (Optional[float]) – HOw much we estimate to pay in LP fees (dollar)
planned_mid_price (Optional[float]) – What was the mid-price of the trading pair when we started to plan this trade.
How many reserve units this trade produces/consumes.
I.e. dollar amount for buys/sells.
price_structure (Optional[TradePricing]) –
The full planned price structure for this trade.
The state of the market at the time of planning the trade, and what fees we assumed we are going to get.
slippage_tolerance (Optional[float]) –
Slippage tolerance for this trade.
See
tradeexecutor.state.trade.TradeExecution.slippage_tolerance
for details.reserve_currency_price (float) –
- Return type:
- has_trade(trade)[source]#
Check if a trade belongs to this position.
- Parameters:
trade (TradeExecution) –
- can_be_closed(epsilon=0.0001)[source]#
There are no tied tokens in this position.
Perform additional check for token amount dust caused by rounding errors.
- Return type:
- get_net_quantity()[source]#
The difference in the quantity of assets bought and sold to date.
- Return type:
- get_price_at_open()[source]#
Get the price of the position at open.
Include only the first trade that opened the position. Calculate based on the executed price.
- Return type:
- get_quantity_at_open()[source]#
Get the quanaity of the asset the position at open.
Include only the first trade that opened the position. Calculate based on the executed price.
- Return type:
- get_realised_profit_usd()[source]#
Calculates the profit & loss (P&L) that has been ‘realised’ via two opposing asset transactions in the Position to date.
- get_unrealised_profit_usd()[source]#
Calculate the position unrealised profit.
Calculates the profit & loss (P&L) that has yet to be ‘realised’ in the remaining non-zero quantity of assets, due to the current market price.
- Returns:
profit in dollar
- Return type:
- get_total_profit_percent()[source]#
How much % we have made profit so far.
- Returns:
0 if profit calculation cannot be made yet
- Return type:
- get_total_profit_at_timestamp(timestamp)[source]#
Get the profit of the position what it was at a certain point of time.
Include realised and unrealised profit.
- get_freeze_reason()[source]#
Return the revert reason why this position is frozen.
Get the revert reason of the last blockchain transaction, assumed to be swap, for this trade.
If this position has been unfrozen, then return the last freeze reason.
- get_last_tx_hash()[source]#
Get the latest transaction performed for this position.
It’s the tx of the trade that was made for this position.
TODO: Deprecate
- get_value_at_open()[source]#
How much the position had value tied after its open.
Calculate the value after the first trade.
- Return type:
- get_value_at_close()[source]#
How much the position had value tied after its close.
Calculate the value after the last trade
- Return type:
- get_capital_tied_at_open_pct()[source]#
Calculate how much portfolio capital was risk when this position was opened.
This is based on the opening values, any position adjustment after open is ignored
Assume capital is tied to the position and we can never release it.
Assume no stop loss is used, or it cannto be trigged
See also
get_loss_risk_at_open_pct()
.- Returns:
Percent of the portfolio value
- Return type:
- get_loss_risk_at_open()[source]#
What is the maximum risk of this position.
The maximum risk is the amount of portfolio we can lose at one position. It is calculated as position stop loss / position total size. We assume stop losses always trigged perfectly and we do not lose (too much) on the stop loss trigger.
- Returns:
Dollar value of the risked capital
- Return type:
- get_loss_risk_at_open_pct()[source]#
What is the maximum risk of this position.
Risk relative to the portfolio size.
See also
get_loss_risk_at_open_pct()
.- Returns:
Percent of total portfolio value
- Return type:
- get_realised_profit_percent()[source]#
Calculated life-time profit over this position.
Calculate how many percent profit this position made, relative to all trades taken over the life time of the position.
See Profitability calculations for more details.
- Returns:
If the position made 1% profit returns 1.01.
- Return type:
- get_size_relative_realised_profit_percent()[source]#
Calculated life-time profit over this position.
Calculate how many percent this profit made profit, adjusted to the position size compared to the available strategy equity at the opening of the position.
This is mostly useful to calculate the strategy performance independent of funding deposits and redemptions.
See Profitability calculations for more details.
- Returns:
If the position made 1% profit returns 1.01.
- Return type:
- get_duration()[source]#
How long this position was held. :return: None if the position is still open
- Return type:
datetime.timedelta | None
- get_total_lp_fees_paid()[source]#
Get the total amount of swap fees paid in the position. Includes all trades.
- Return type:
- get_orignal_stop_loss()[source]#
Get the original stop loss value when this position was opened.
Setting
trailing_stop_loss
will cause stop_loss to be updated. We can still fetch the original stop loss fromtrigger_updates
.
- calculate_quantity_usd_value(quantity)[source]#
Calculate value of asset amount using the latest known price.
- add_notes_message(msg)[source]#
Add a new message to the notes field.
Messages are newline separated.
- Parameters:
msg (str) –
- add_balance_update_event(event)[source]#
Include a new balance update event
- Raises:
BalanceUpdateEventAlreadyAdded – In the case of a duplicate and event id is already used.
- Parameters:
event (BalanceUpdate) –
- __init__(position_id, pair, opened_at, last_pricing_at, last_token_price, last_reserve_price, reserve_currency, trades=<factory>, closed_at=None, frozen_at=None, unfrozen_at=None, last_trade_at=None, portfolio_value_at_open=None, stop_loss=None, take_profit=None, trailing_stop_loss_pct=None, notes=None, balance_updates=<factory>, trigger_updates=<factory>)#
- Parameters:
position_id (int) –
pair (TradingPairIdentifier) –
opened_at (datetime) –
last_pricing_at (datetime) –
last_token_price (float) –
last_reserve_price (float) –
reserve_currency (AssetIdentifier) –
trades (Dict[int, TradeExecution]) –
balance_updates (Dict[int, BalanceUpdate]) –
trigger_updates (List[TriggerPriceUpdate]) –
- Return type:
None