def try_buy(self, code: str, what: str, order_price: int = None, memo: str = None): if self.wallet.has(code): return if len(self.wallet.holdings) >= self.max_holding_count: logging.warning('The number of holdings has reached the maximum holdings.') return if not order_price: detail = list(stocks.get_details([code]))[0] order_price = detail.price order_count = int(100_0000 / order_price) order_total = order_price * order_count try: traders.buy(code=code, price=order_price, count=order_count) self.wallet.put(Holding(created=datetime.now(), code=code, count=order_count, price=order_price)) OrderRecord( what=what, order_type='BUY', code=code, name=stocks.get_name(code), order_price=order_price, order_count=order_count, total=order_total, memo=memo ).summit(logger=self.logger, warren_session=self.warren_session) except: logging.exception('Failed to try to buy ' + code)
def try_sell(self, code: str, what: str, order_price: int = None): return # fixme if not self.wallet.has(code): return holding = self.wallet.get(code) if not order_price: detail = list(stocks.get_details([code]))[0] order_price = detail.price order_total = order_price * holding.quantity holding_total = holding.price * holding.quantity try: traders.sell(code=code, price=order_price, count=holding.quantity) self.wallet.delete(code) OrderRecord( what=what, order_type='SELL', code=code, name=stocks.get_name(code), order_price=order_price, order_count=holding.quantity, total=order_total, earning_price=order_total - holding_total, earning_rate=calc.earnings_ratio(holding.price, order_price) ).summit(logger=self.logger, warren_session=self.warren_session) except: logging.exception('Failed to try to sell ' + code)
def sell(self, dt: datetime, code, sell_price, sell_amount: float): holding = self.get(code) # 매도 수량 계산 sell_count = math.ceil(holding.count * sell_amount) # 보유 수량에서 매도 수량 만큼 차감 holding.count = holding.count - sell_count if holding.count == 0: # 전량 매도 self.holdings.remove(holding) earnings = sell_price * sell_count - holding.price * sell_count self.earnings += earnings tokens = [ dt, # 시각 'SELL', # 구분 code, # 종목코드 stocks.get_name(code), # 종목명 details.get(code).capitalization(), # 시총 sell_price, # 주문가 sell_count, # 주문수량 sell_price * sell_count, # 주문총액 calc.earnings_ratio(holding.price, sell_price), # 수익율 earnings, # 수익금 holding.count, # 잔여수량 ] logger.critical(', '.join([str(token) for token in tokens]))
def __init__(self, code: str, begin: date, end: date): self.wallet = Wallet() self.code = code self.result = SimulationResult(code=normalize(self.code), name=stocks.find(code).name, begin=begin, end=end) self.candle_provider = creon.provider.MinuteCandleProvdider( code, begin, end) self.candle_provider.subscribers.append(self.on_candle) self.candle_provider.subscribers.append( lambda candle: self.result.candles.append(candle)) self.daily_candles: List[Candle] = charts.request_by_term( code=code, chart_type=charts.ChartType.DAY, begin=begin - timedelta(days=200), end=end) if not self.daily_candles: raise NotEnoughChartException(code, details.get(code).name) self.daily_candles.sort( key=lambda candle: datetime.combine(candle.date, candle.time)) if not self.daily_candles[0].date < begin < self.daily_candles[-1].date: raise NotEnoughChartException(code=code, name=stocks.get_name(code)) self.daily_candles: Dict[date, Candle] = { candle.date: candle for candle in self.daily_candles } self.last_candle: Optional[Candle] = None
def ma(self, dt: date, length: int, cur_price: int = 0, pos: int = 0): values = [ candle.close for candle in self.daily_candles.values() if candle.date < dt ] + [cur_price] if pos: values = values[-length + pos:pos] else: values = values[-length:] if length > len(values): raise NotEnoughChartException(self.code, stocks.get_name(self.code)) return sum(values) / length
def buy(self, dt: datetime, code, count, price): total = count * price self.holdings.append(Holding(code, count, price)) tokens = [ dt, # 주문시각 'BUY', # 구분 code, # 종목코드 stocks.get_name(code), # 종목명 details.get(code).capitalization(), price, # 주문가 count, # 주문수량 total, # 주문총액 'N/A', # 수익율 'N/A', # 수익금 count, # 잔여수량 ] logger.critical(', '.join([str(token) for token in tokens]))
# if code in executed or stocks.get_name(code) in executed: # continue logger.info( f'[{count}/{len(codes)}] {stocks.get_name(code)} - 시총: {details.get(code).capitalization()}' ) for term in terms: begin = term.begin end = term.end ep = None try: logger.info(f'{begin} ~ {end}') ep = BreakAbove5MaEventSimulator(code, begin=begin, end=end) ep.start() except NotEnoughChartException as e: logger.warning(str(e)) finally: if ep: ep.candle_provider.stop() logger.critical(time.time() - start_time) if __name__ == '__main__': available_codes.sort(key=lambda code: details.get(code).capitalization()) main([ code for code in available_codes if '스팩' not in stocks.get_name(code) ])