from django.test import TestCase from core.trading.crossfilter import check_conflicting_position, check_existing_position class CrossfilterTestCase(TestCase): def test_conflict_position(self): position = { "symbol": "EUR_USD", "base": "EUR", "quote": "USD", "side": "long", "units": "1", } trade_cast = { "symbol": "GBP_EUR", "base": "GBP", "quote": "EUR", "side": "long", "units": "1", } opposite = "short" check = check_conflicting_position( func="entry", position=position, open_base=position["base"], open_quote=position["quote"], open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_base=trade_cast["base"], new_quote=trade_cast["quote"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertEqual(check["action"], "rejected") def test_conflict_position_quote(self): position = { "symbol": "EUR_USD", "base": "EUR", "quote": "USD", "side": "long", "units": "1", } trade_cast = { "symbol": "USD_JPY", "base": "USD", "quote": "JPY", "side": "long", "units": "1", } opposite = "short" check = check_conflicting_position( func="entry", position=position, open_base=position["base"], open_quote=position["quote"], open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_base=trade_cast["base"], new_quote=trade_cast["quote"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertEqual(check["action"], "rejected") def test_conflict_position_invert_allowed(self): position = { "symbol": "EUR_USD", "base": "EUR", "quote": "USD", "side": "long", "units": "1", } trade_cast = { "symbol": "GBP_EUR", "base": "GBP", "quote": "EUR", "side": "short", "units": "1", } opposite = "long" check = check_conflicting_position( func="entry", position=position, open_base=position["base"], open_quote=position["quote"], open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_base=trade_cast["base"], new_quote=trade_cast["quote"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertFalse(check) def test_conflict_position_quote_invert_allowed(self): position = { "symbol": "EUR_USD", "base": "EUR", "quote": "USD", "side": "short", "units": "1", } trade_cast = { "symbol": "USD_JPY", "base": "USD", "quote": "JPY", "side": "long", "units": "1", } opposite = "short" check = check_conflicting_position( func="entry", position=position, open_base=position["base"], open_quote=position["quote"], open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_base=trade_cast["base"], new_quote=trade_cast["quote"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertFalse(check) def test_conflict_position_identical_allowed(self): position = { "symbol": "EUR_USD", "base": "EUR", "quote": "USD", "side": "long", "units": "1", } trade_cast = { "symbol": "EUR_USD", "base": "EUR", "quote": "USD", "side": "long", "units": "1", } opposite = "short" check = check_conflicting_position( func="entry", position=position, open_base=position["base"], open_quote=position["quote"], open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_base=trade_cast["base"], new_quote=trade_cast["quote"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertFalse(check) def test_existing_position_fail(self): """ Check we cannot enter a short if we already have a long. """ position = {"symbol": "EUR_USD", "side": "long", "units": "1"} trade_cast = {"symbol": "EUR_USD", "side": "short", "units": "1"} opposite = "long" check = check_existing_position( func="entry", position=position, open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertEqual(check["action"], "rejected") def test_existing_position_flip_fail(self): """ Check we cannot enter a long if we already have a short. """ position = {"symbol": "EUR_USD", "side": "short", "units": "1"} trade_cast = {"symbol": "EUR_USD", "side": "long", "units": "1"} opposite = "short" check = check_existing_position( func="entry", position=position, open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertEqual(check["action"], "rejected") def test_existing_position_exit(self): position = {"symbol": "EUR_USD", "side": "long", "units": "1"} trade_cast = {"symbol": "EUR_USD", "side": "short", "units": "1"} opposite = "long" check = check_existing_position( func="exit", position=position, open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertEqual(check["action"], "close") self.assertEqual(check["positions"], position) self.assertEqual(check["side"], opposite) def test_existing_position_exit_no_units(self): position = {"symbol": "EUR_USD", "side": "long", "units": "0"} trade_cast = {"symbol": "EUR_USD", "side": "short", "units": "1"} opposite = "long" check = check_existing_position( func="exit", position=position, open_side=position["side"], open_symbol=position["symbol"], open_units=position["units"], new_side=trade_cast["side"], new_symbol=trade_cast["symbol"], trade_side_opposite=opposite, ) self.assertFalse(check)