def import_from_csv_yahoo(self) -> str: BaseService._truncate(EPD) files: List[str] = FileUtils.get_files(AppConsts.ETF_PRICE_FOLDER, is_full=True) for file in files: symbol: str = FileUtils.get_wo_ext(FileUtils.get_base_name(file)) org_symbol: SM = self.__stock_service.get_symbol( symbol, AppConsts.INSTRUMENT_ETF) if not org_symbol: continue records: List[Dict] = CsvUtils.parse_as_dict(file) models: List[Any] = [] for record in records: models.append(( org_symbol.id, DateUtils.get_date(record.get(AppConsts.YAHOO_KEY_DATE), AppConsts.YAHOO_DATE_FORMAT), NumberUtils.to_float(record.get(AppConsts.YAHOO_KEY_OPEN)), NumberUtils.to_float(record.get(AppConsts.YAHOO_KEY_HIGH)), NumberUtils.to_float(record.get(AppConsts.YAHOO_KEY_LOW)), NumberUtils.to_float(record.get( AppConsts.YAHOO_KEY_CLOSE)), NumberUtils.to_int(record.get(AppConsts.YAHOO_KEY_VOLUME)), )) BaseService._insert_bulk(EPD, models) return "1"
def import_from_csv_filedates(self) -> str: file: str = FileUtils.get_file(AppConsts.INCOME_STMT_FILE) records: List[Dict] = CsvUtils.parse_as_dict(file) for record in records: if not self.__is_valid_intrinio_record_for_filedates(record): continue symbol: str = record.get(AppConsts.INTRINIO_KEY_INC_STMT_TICKER) fiscal_period: str = record.get( AppConsts.INTRINIO_KEY_INC_STMT_FISC_PD) year: int = NumberUtils.to_int( record.get(AppConsts.INTRINIO_KEY_INC_STMT_FISC_YR)) quarter: int = self.__get_quarter(fiscal_period) file_date: date = DateUtils.get_date( record.get(AppConsts.INTRINIO_KEY_INC_STMT_FILE_DTE), AppConsts.INTRINIO_FILE_DTE_FMT) if not file_date or quarter == 4: continue org_symbol: SM = self.__stock_service.get_symbol( symbol, AppConsts.INSTRUMENT_STOCK) if not org_symbol: continue org_fn: FN = self.__stock_service.get_financial( org_symbol.id, year, quarter) if not org_fn: continue org_fn.file_date = file_date BaseService._update() return "1"
def test_get_date_should_not_return_date_if_invalid_request(self) -> None: # ARRANGE none_datestr_case: str = None empty_datestr_case: str = '' whitespace_datestr_case: str = ' ' invalid_datestr_case: str = 'foo' invalid_datestr_type_case: int = 1 none_fmt_case: str = None empty_fmt_case: str = '' whitespace_fmt_case: str = ' ' invalid_fmt_case: str = 'bar' invalid_fmt_type_case: int = 1 # ACT ret_none_datestr_case: date = DateUtils.get_date( none_datestr_case, 'fake') ret_empty_datestr_case: date = DateUtils.get_date( empty_datestr_case, 'fake') ret_whitespace_datestr_case: date = DateUtils.get_date( whitespace_datestr_case, 'fake') ret_invalid_datestr_case: date = DateUtils.get_date( invalid_datestr_case, '%Y-%m-%d') ret_invalid_datestr_type_case: date = DateUtils.get_date( invalid_datestr_type_case, '%Y-%m-%d') ret_none_fmt_case: date = DateUtils.get_date('fake', none_fmt_case) ret_empty_fmt_case: date = DateUtils.get_date('fake', empty_fmt_case) ret_whitespace_fmt_case: date = DateUtils.get_date( 'fake', whitespace_fmt_case) ret_invalid_fmt_case: date = DateUtils.get_date( '2001-01-01', invalid_fmt_case) ret_invalid_fmt_type_case: date = DateUtils.get_date( '2001-01-01', invalid_fmt_type_case) # ASSERT self.assertIsNone(ret_none_datestr_case) self.assertIsNone(ret_empty_datestr_case) self.assertIsNone(ret_whitespace_datestr_case) self.assertIsNone(ret_invalid_datestr_case) self.assertIsNone(ret_invalid_datestr_type_case) self.assertIsNone(ret_none_fmt_case) self.assertIsNone(ret_empty_fmt_case) self.assertIsNone(ret_whitespace_fmt_case) self.assertIsNone(ret_invalid_fmt_case) self.assertIsNone(ret_invalid_fmt_type_case)
def import_from_csv_incomestatements(self) -> str: BaseService._truncate(FN) file: str = FileUtils.get_file(AppConsts.INCOME_STMT_FILE) records: List[Dict] = CsvUtils.parse_as_dict(file) models: List[Any] = [] for record in records: if not self.__is_valid_intrinio_record(record): continue symbol: str = record.get(AppConsts.INTRINIO_KEY_INC_STMT_TICKER) fiscal_period: str = record.get( AppConsts.INTRINIO_KEY_INC_STMT_FISC_PD) org_symbol: SM = self.__stock_service.get_symbol( symbol, AppConsts.INSTRUMENT_STOCK) if not org_symbol: continue quarter_end_dte: date = DateUtils.get_date( record.get(AppConsts.INTRINIO_KEY_INC_STMT_END_DTE), AppConsts.INTRINIO_END_DTE_FMT) file_date: date = DateUtils.get_date( record.get(AppConsts.INTRINIO_KEY_INC_STMT_FILE_DTE), AppConsts.INTRINIO_FILE_DTE_FMT) models.append( (org_symbol.id, record.get(AppConsts.INTRINIO_KEY_INC_STMT_FISC_YR), self.__get_quarter(fiscal_period), quarter_end_dte, file_date, None, NumberUtils.to_float( record.get(AppConsts.INTRINIO_KEY_INC_STMT_TTLREV)), NumberUtils.to_float( record.get(AppConsts.INTRINIO_KEY_INC_STMT_TTLPROF)), NumberUtils.to_float( record.get(AppConsts.INTRINIO_KEY_INC_STMT_TTLOPINC)), NumberUtils.to_float( record.get(AppConsts.INTRINIO_KEY_INC_STMT_NETINC)), None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None)) BaseService._insert_bulk(FN, models) return "1"
def test_get_date_should_return_date_if_valid_request(self) -> None: # ARRANGE test_date: str = '2001-01-01' fmt: str = '%Y-%m-%d' # ACT ret_test_date: date = DateUtils.get_date(test_date, fmt) # ASSERT self.assertIsNotNone(ret_test_date) self.assertEqual(2001, ret_test_date.year) self.assertEqual(1, ret_test_date.month) self.assertEqual(1, ret_test_date.day)
def import_from_csv_prices(self) -> str: BaseService._truncate(SPD) files: List[str] = FileUtils.get_files(AppConsts.STOCK_PRICE_FOLDER, is_full=True) for file in files: symbol: str = FileUtils.get_wo_ext(FileUtils.get_base_name(file)) org_symbol: SM = self.__stock_service.get_symbol( symbol, AppConsts.INSTRUMENT_STOCK) if not org_symbol: continue records: List[List[str]] = CsvUtils.parse_as_list(file) if not records: continue for record in records: record[AppConsts.KIBOT_IDX_DATE] = DateUtils.get_date( record[AppConsts.KIBOT_IDX_DATE], AppConsts.KIBOT_DATE_FORMAT) record.insert(0, org_symbol.id) BaseService._insert_bulk(SPD, records) return "1"
def date_to_obj(self) -> date: return DateUtils.get_date(self._date_to, '%Y-%m-%d')
def date_from_obj(self) -> date: return DateUtils.get_date(self._date_from, '%Y-%m-%d')
def sync_orders(self) -> int: errors: List[Exception] = [] try: req: GetTradeOrdersRequest = GetTradeOrdersRequest() req.status = [ AppConsts.ORDER_STATUS_SUBMITTED_ENTRY, AppConsts.ORDER_STATUS_SUBMITTED_EXIT ] orders: List[TradeOrderCustom] = self.get_trade_orders(req) if not orders: LogUtils.debug('No orders submitted') for order in orders: try: LogUtils.debug('Sync order for = {0}'.format( order.symbol_master.symbol)) resp: Order = None if order.trade_order.status == AppConsts.ORDER_STATUS_SUBMITTED_ENTRY: resp = self.__alpaca_client.get_order( order.trade_order.alpaca_id) elif order.trade_order.status == AppConsts.ORDER_STATUS_SUBMITTED_EXIT: resp = self.__alpaca_client.get_order( order.trade_order.exit_alpaca_id) if resp: org: TradeOrder = BaseService._get_by_id( TradeOrder, order.trade_order.id) if not org: raise NotFoundException('TradeOrder', 'id', order.trade_order.id) if order.trade_order.status == AppConsts.ORDER_STATUS_SUBMITTED_ENTRY \ and resp.status == AppConsts.ALPACA_ORDER_STATUS_FILLED: org.status = AppConsts.ORDER_STATUS_IN_POSITION org.actual_qty = NumberUtils.to_int( resp.filled_qty) org.actual_entry_price = NumberUtils.to_float( resp.filled_avg_price) org.modified = datetime.now() BaseService._update() elif order.trade_order.status == AppConsts.ORDER_STATUS_SUBMITTED_ENTRY \ and resp.status == AppConsts.ALPACA_ORDER_STATUS_CANCELLED: org.status = AppConsts.ORDER_STATUS_CANCELLED_ENTRY org.modified = datetime.now() BaseService._update() elif order.trade_order.status == AppConsts.ORDER_STATUS_SUBMITTED_EXIT \ and resp.status == AppConsts.ALPACA_ORDER_STATUS_FILLED: exit_price: StockPriceDaily = self.__stock_service.get_single_stock_price_daily( order.symbol_master.id, DateUtils.get_date( datetime.today().strftime('%Y-%m-%d'), '%Y-%m-%d')) if exit_price: org.exit_stock_price_daily_id = exit_price.id org.status = AppConsts.ORDER_STATUS_COMPLETED org.actual_exit_price = NumberUtils.to_float( resp.filled_avg_price) org.modified = datetime.now() BaseService._update() elif order.trade_order.status == AppConsts.ORDER_STATUS_SUBMITTED_EXIT \ and resp.status == AppConsts.ALPACA_ORDER_STATUS_CANCELLED: org.status = AppConsts.ORDER_STATUS_CANCELLED_EXIT org.modified = datetime.now() BaseService._update() raise Exception('Exit Error = {0}'.format( resp.status)) else: raise Exception('Sync Status = {0}'.format( resp.status)) else: raise NotFoundException('Alpaca Order', 'id', order.trade_order.alpaca_id) except Exception as ex: LogUtils.error('Sync Orders Error', ex) errors.append(ex) except Exception as ex: LogUtils.error('Sync Orders Error', ex) errors.append(ex) finally: self.__email_client.send_html( subject=AppConsts.EMAIL_SUBJECT_SYNC_ORDERS, template_path=AppConsts.TEMPLATE_PATH_SYNC_ORDERS, model={'errors': errors}) return 1