def test_close_position_take_profit(self): p1 = Position(side=Side.BUY, qty=1, pos_value=100, take_profit=0.04, stop_loss=-0.05) p2 = Position(side=Side.BUY, qty=1, pos_value=90, take_profit=0.06, stop_loss=-0.05) p3 = Position(side=Side.SELL, qty=1, pos_value=80, take_profit=0.04, stop_loss=-0.03) self.portfolio.positions.append(p1) self.portfolio.positions.append(p2) self.portfolio.positions.append(p3) self.portfolio.compute_liquid_value() self.assertEqual(1275.5, self.portfolio.liquidative_value) self.portfolio.close_position() self.assertEqual(1, len(self.portfolio.positions)) pos = self.portfolio.positions[0] self.assertEqual(0.06, pos.take_profit) self.assertEqual(1275.5, self.portfolio.liquidative_value)
def test_liquidative_value_with_pos(self): p1 = Position(side=Side.BUY, qty=1, pos_value=100) p2 = Position(side=Side.BUY, qty=1, pos_value=90) p3 = Position(side=Side.SELL, qty=1, pos_value=80) self.portfolio.positions.append(p1) self.portfolio.positions.append(p2) self.portfolio.positions.append(p3) self.portfolio.compute_liquid_value() self.assertEqual(1275.5, self.portfolio.liquidative_value)
def make_operation(self, side: Side, qty: float, transaction_fee: float, take_profit: float = None, stop_loss: float = None): if side is Side.OTHER: return if len(self.positions) > 0: self.in_buy_position = True if side is Side.SELL and not self.in_buy_position: raise PortfolioException( 'Cannot Sell something not in the portfolio') elif side is Side.SELL and self.in_buy_position: logger.info('Closing all buy positions because of selling signal') self.close_position(force=True) else: notional = qty * self.asset_value if notional > self.money: raise NotEnoughMoneyException( f'Cannot {side} {qty} because {notional} > {self.money}') self.money -= notional + transaction_fee pos = Position(as_of_date=self.as_of_date, qty=qty, side=side, pos_value=notional, take_profit=take_profit, stop_loss=stop_loss) self.positions.append(pos)
def test_close_position_stop_loss(self): self.portfolio.asset_perf = -0.04 p1 = Position(side=Side.BUY, qty=1, pos_value=100, take_profit=0.04, stop_loss=-0.05) p2 = Position(side=Side.BUY, qty=1, pos_value=90, take_profit=0.06, stop_loss=-0.05) p3 = Position(side=Side.SELL, qty=1, pos_value=80, take_profit=0.04, stop_loss=-0.03) self.portfolio.positions.append(p1) self.portfolio.positions.append(p2) self.portfolio.positions.append(p3) self.portfolio.compute_liquid_value() self.portfolio.close_position() self.assertEqual(2, len(self.portfolio.positions))
def make_operation(self, side: Side, qty: float, transaction_fee: float, take_profit: float = None, stop_loss: float = None): if side is Side.OTHER: return notional = qty * self.asset_value if notional > self.money: raise NotEnoughMoneyException(f'Cannot {side} {qty} because {notional} > {self.money}') self.money -= notional + transaction_fee pos = Position( as_of_date=self.as_of_date, qty=qty, side=side, pos_value=notional, take_profit=take_profit, stop_loss=stop_loss ) self.positions.append(pos)
def setUp(self): self.position = Position( qty=1, pos_value=100, ) print()
class TestPosition(unittest.TestCase): def setUp(self): self.position = Position( qty=1, pos_value=100, ) print() def tearDown(self): pass def test_compute_pos_value_buy(self): perf = 0.05 self.position.side = Side.BUY self.position.compute_pos_value(perf) self.assertEqual(105, self.position.pos_value) def test_compute_pos_value_double_qty_buy(self): perf = 0.05 self.position.side = Side.BUY self.position.qty *= 2 self.position.pos_value *= 2 self.position.compute_pos_value(perf) self.assertEqual(210, self.position.pos_value) def test_compute_pos_value_sell(self): perf = 0.05 self.position.side = Side.SELL self.position.compute_pos_value(perf) self.assertEqual(95, self.position.pos_value) def test_compute_pos_value_double_qty_sell(self): perf = 0.05 self.position.side = Side.SELL self.position.qty *= 2 self.position.pos_value *= 2 self.position.compute_pos_value(perf) self.assertEqual(190, self.position.pos_value) def test_compute_pos_value_sell_neg(self): perf = -0.05 self.position.side = Side.SELL self.position.compute_pos_value(perf) self.assertEqual(105, self.position.pos_value) def test_not_take_profit(self): perf = 0.04 self.position.take_profit = 0.05 self.position.side = Side.BUY self.position.compute_pos_value(perf) self.assertEqual(False, self.position.close_position) def test_not_stop_loss(self): perf = -0.04 self.position.stop_loss = -0.05 self.position.side = Side.BUY self.position.compute_pos_value(perf) self.assertEqual(False, self.position.close_position) def test_take_profit(self): perf = 0.06 self.position.take_profit = 0.05 self.position.side = Side.BUY self.position.compute_pos_value(perf) self.assertEqual(True, self.position.close_position) def test_stop_loss(self): perf = -0.06 self.position.stop_loss = -0.05 self.position.side = Side.BUY self.position.compute_pos_value(perf) self.assertEqual(True, self.position.close_position)