def test_pcm_fixed_weight_optimiser_fixed_alpha_weights_call_end_to_end( helpers): """ Tests the full portfolio base class logic for carrying out rebalancing. TODO: DataHandler is mocked. A non-disk based data source should be utilised instead. """ first_dt = pd.Timestamp('2019-01-01 15:00:00', tz=pytz.utc) asset_list = ['EQ:SPY', 'EQ:AGG', 'EQ:TLT', 'EQ:GLD'] initial_funds = 1e6 account_id = '1234' port_id = '1234' cash_buffer_perc = 0.05 exchange = SimulatedExchange(first_dt) universe = StaticUniverse(asset_list) mock_asset_prices_first = { 'EQ:SPY': 56.87, 'EQ:AGG': 219.45, 'EQ:TLT': 178.33, 'EQ:GLD': 534.21 } data_handler = Mock() data_handler.get_asset_latest_ask_price.side_effect = \ lambda self, x: mock_asset_prices_first[x] broker = SimulatedBroker(first_dt, exchange, data_handler, account_id, initial_funds=initial_funds) broker.create_portfolio(port_id, 'Portfolio') broker.subscribe_funds_to_portfolio(port_id, initial_funds) order_sizer = DollarWeightedCashBufferedOrderSizeGeneration( broker, port_id, data_handler, cash_buffer_perc) optimiser = FixedWeightPortfolioOptimiser(data_handler) alpha_weights = { 'EQ:SPY': 0.345, 'EQ:AGG': 0.611, 'EQ:TLT': 0.870, 'EQ:GLD': 0.0765 } alpha_model = FixedSignalsAlphaModel(alpha_weights) pcm = PortfolioConstructionModel(broker, port_id, universe, order_sizer, optimiser, alpha_model) result_first = pcm(first_dt) expected_first = [ Order(first_dt, 'EQ:AGG', 1390), Order(first_dt, 'EQ:GLD', 71), Order(first_dt, 'EQ:SPY', 3029), Order(first_dt, 'EQ:TLT', 2436) ] helpers.assert_order_lists_equal(result_first, expected_first)
def test_create_zero_target_weight_vector(description, full_assets, expected): """ Tests the _create_zero_target_weight_vector method of the PortfolioConstructionModel base class. """ port_id = '1234' broker = Mock() universe = Mock() order_sizer = Mock() optimiser = Mock() pcm = PortfolioConstructionModel(broker, port_id, universe, order_sizer, optimiser) result = pcm._create_zero_target_weight_vector(full_assets) assert result == expected
def test_generate_rebalance_orders(helpers, description, target_portfolio, current_portfolio, expected): """ Tests the _generate_rebalance_orders method of the PortfolioConstructionModel base class. """ port_id = '1234' broker = Mock() universe = Mock() order_sizer = Mock() optimiser = Mock() pcm = PortfolioConstructionModel(broker, port_id, universe, order_sizer, optimiser) result = pcm._generate_rebalance_orders(SENTINEL_DT, target_portfolio, current_portfolio) helpers.assert_order_lists_equal(result, expected)
def test_obtain_full_asset_list(description, port_dict, uni_assets, expected): """ Tests the _obtain_full_asset_list method of the PortfolioConstructionModel base class. """ port_id = '1234' broker = Mock() broker.get_portfolio_as_dict.return_value = port_dict universe = Mock() universe.get_assets.return_value = uni_assets order_sizer = Mock() optimiser = Mock() pcm = PortfolioConstructionModel(broker, port_id, universe, order_sizer, optimiser) result = pcm._obtain_full_asset_list(SENTINEL_DT) assert result == expected
def _initialise_models(self): """ Initialise the various models for the quantitative trading strategy. This includes the portfolio construction and the execution. TODO: Add TransactionCostModel TODO: Ensure this is dynamically generated from config. """ # Portfolio Construction order_sizer = DollarWeightedCashBufferedOrderSizeGeneration( self.broker, self.broker_portfolio_id, self.data_handler, cash_buffer_percentage=self.cash_buffer_percentage) optimiser = FixedWeightPortfolioOptimiser( data_handler=self.data_handler) self.portfolio_construction_model = PortfolioConstructionModel( self.broker, self.broker_portfolio_id, self.universe, order_sizer, optimiser, alpha_model=self.alpha_model, risk_model=self.risk_model, data_handler=self.data_handler) # Execution execution_algo = MarketOrderExecutionAlgorithm() self.execution_handler = ExecutionHandler( self.broker, self.broker_portfolio_id, self.universe, submit_orders=self.submit_orders, execution_algo=execution_algo, data_handler=self.data_handler)
def _initialise_models(self, **kwargs): """ Initialise the various models for the quantitative trading strategy. This includes the portfolio construction and the execution. TODO: Add TransactionCostModel TODO: Ensure this is dynamically generated from config. """ # Determine the appropriate order sizing mechanism order_sizer = self._create_order_sizer(**kwargs) # TODO: Allow optimiser to be generated from config optimiser = FixedWeightPortfolioOptimiser( data_handler=self.data_handler) # Generate the portfolio construction self.portfolio_construction_model = PortfolioConstructionModel( self.broker, self.broker_portfolio_id, self.universe, order_sizer, optimiser, alpha_model=self.alpha_model, risk_model=self.risk_model, data_handler=self.data_handler) # Execution execution_algo = MarketOrderExecutionAlgorithm() self.execution_handler = ExecutionHandler( self.broker, self.broker_portfolio_id, self.universe, submit_orders=self.submit_orders, execution_algo=execution_algo, data_handler=self.data_handler)