Exemplo n.º 1
0
    def set_bidask_monitoring(self, code):
        bidask = CybosBidAskTick()
        bidask.set_output(self)
        bidask.set_target(code)

        self.montoring_bidask.append(bidask)
        logger.print('START Monitoring BA', code)
Exemplo n.º 2
0
    def handle_traded(self, code, is_buy, result):
        logger.print('handle_traded', code, is_buy)
        if code in self.on_market_queue:
            on_market_item = self.on_market_queue[code]
            traded_quantity = result['quantity']
            if on_market_item['quantity'] == traded_quantity:
                if is_buy:  
                    if code in self.long_list: # Partiallty traded and done
                        self.long_list[code] += traded_quantity 
                    else:
                        self.long_list[code] = traded_quantity
                    self.on_market_queue.pop(code, None)
                else:
                    self.long_list.pop(code, None)
                    self.on_market_queue.pop(code, None)
            else:
                if code not in self.long_list:
                    self.long_list[code] = 0

                if is_buy:
                    self.long_list[code] += traded_quantity
                else:
                    self.long_list[code] -= traded_quantity
                on_market_item['quantity'] -= traded_quantity
                QTimer.singleShot(10000, self._check_on_market_queue)
        else:
            logger.error('code is not in on market queue', code)
Exemplo n.º 3
0
    def _check_on_market_queue(self):
        logger.print('check on market queue', len(self.on_market_queue))
        if len(self.on_market_queue) == 0:  # Try to avoid to call blockrequest
            return

        orders = self.order_in_queue.request()
        # Use Cp5339 and verify not traded items
        for k, v in self.on_market_queue.items():
            if v['order_modify_type'] == OrderTransaction.NORMAL and datetime.now() - v['date'] > timedelta(seconds=8):
                in_bills = None
                for order in orders:
                    if order['number'] == v['order_number']:
                        in_bills = order
                        break
                if in_bills is None:
                    logger.error('Cannot find matched item in bills')
                    continue

                if v['order_type']: # BUY
                    cancel_order = CancelOrder(self.account_num, self.account_type)
                    record_cancel_order(k, v.copy())
                    cancel_order.cancel_order(v['order_number'], k, 0)
                    v['order_modify_type'] = OrderTransaction.CANCEL
                else:
                    # modify order to sell immediately
                    modify_order = ModifyOrder(self.account_num, self.account_type)
                    record_modify_order(k, v.copy())
                    order_new_num = modify_order.modify_order(v['order_number'], k, 0, self.account_obj.get_ask_price(k, 4))
                    order['number'] = order_new_num
                    v['order_modify_type'] = OrderTransaction.MODIFY
Exemplo n.º 4
0
    def cancel_order(self, order_number, code, amount):
        logger.print('Cancel Order', order_number, code, amount)
        self.obj.SetInputValue(1, order_number)
        self.obj.SetInputValue(2, self.account_num)
        self.obj.SetInputValue(3, self.account_type)
        self.obj.SetInputValue(4, code)
        self.obj.SetInputValue(5, 0)  # 0이면 전량 취소 0, 일단 0으로 고정

        while True:
            ret = self.obj.BlockRequest()
            if ret == 0:
                break
            elif ret == 4:
                if self.conn.request_left_count() <= 0:
                    time.sleep(self.conn.get_remain_time() / 1000)
                continue
            else:
                logger.error('TD0314 Cancel Order Failed')
                return

        if self.obj.GetDibStatus() != 0:
            logger.error('TD0314 Cancel Order Status Error',
                         self.obj.GetDibMsg1())
            return False

        return True
Exemplo n.º 5
0
    def received(self, datas):
        for g in self.graph_adder:
            g.received(datas)

        if self.next_elements is not None and not self.done:
            minsec = datas[0]['time_with_sec']
            hour, minute, second = int(minsec / 10000), int(minsec % 10000 / 100), int(minsec % 100)
            if self.start_minsec is None:
                self.start_minsec = datetime.now()
                self.start_minsec = self.start_minsec.replace(hour = hour, minute = minute, second = second)
                self.df = pd.DataFrame(datas)
            else:
                n = datetime.now()
                n = n.replace(hour = hour, minute = minute, second = second)
                if n - self.start_minsec > timedelta(minutes=self.cont_min):
                    if self.check_dataframe(self.df):
                        #logger.print({'name':self.__class__.__name__, 'type': 'Bool', 'value': 'True'}, minsec)
                        self.next_elements.received([{'name':self.__class__.__name__, 
                                                    'target': datas[-1]['target'],
                                                    'stream': datas[-1]['stream'],
                                                    'date': datas[-1]['date'],
                                                    'value': True, 
                                                    'price': datas[-1]['current_price']}])
                        for g in self.graph_adder:
                            g.set_flag(datas[-1]['date'], 'SUCCESS')
                    else:
                        logger.print(self.__class__.__name__, minsec, 'Fail')
                        for g in self.graph_adder:
                            g.set_flag(datas[-1]['date'], 'FAIL')
                    self.done = True
                else:
                    self.df = pd.concat([self.df, pd.DataFrame(datas)])
Exemplo n.º 6
0
 def received(self, datas):
     if len(self.next_elements) > 0:
         if self.drop_count > 0:
             self.drop_count -= 1
             logger.print('DropDataFilter', datas)
         else:
             for n in self.next_elements:
                 n.received(datas)
Exemplo n.º 7
0
    def setup_stream(self, pipelines):
        for p in pipelines:
            self.streams.append(p['stream'])

        for stream in self.streams:
            stream.set_target(self.target)

        logger.print('stream set_target done')
Exemplo n.º 8
0
    def _check_order_wait_queue(self):
        logger.print('check order wait timeout')
        remove_keys = []
        for k, v in self.order_wait_queue.items():
            if datetime.now() - v['date'] > timedelta(seconds=8):
                logger.error('Order queue not processed(will be removed)', k)
                remove_keys.append(k)

        for k in remove_keys:
            logger.print('remove key', k)
            self.order_wait_queue.pop(k, None)
Exemplo n.º 9
0
 def handle_edited(self, code, is_buy, result):
     logger.print('handle_edited', code, is_buy)
     if code in self.on_market_queue:
         on_market_item = self.on_market_queue[code]
         if on_market_item['order_modify_type'] == OrderTransaction.CANCEL:
             if on_market_item['order_number'] != result['order_num']:
                 logger.error('TODO order number is not matched')
             self.on_market_queue.pop(code, None)
         elif on_market_item['order_modify_type'] == OrderTransaction.MODIFY:
             logger.print('ORDER MODIFY SUCCESS', str(result))
     else:
         logger.error('code is not in on market queue(editied)', code)
Exemplo n.º 10
0
    def set_target(self, target):
        code = target.split(':')[1]
        self.target_code = code
        day_code = code + '_D'
        stock = MongoClient(db.HOME_MONGO_ADDRESS)['stock']

        s = time_converter.datetime_to_intdate(self.from_date)
        f = time_converter.datetime_to_intdate(self.until_date)
        cursor = stock[day_code].find({'0': {'$gte': s, '$lte': f}})
        self.data = list(cursor)

        logger.print(target, 'Length', len(self.data))
Exemplo n.º 11
0
def _start_target(queue, job_info):
    app = QCoreApplication([])
    logger.setup_client(log_queue, job_info[0])
    logger.print('PROCESS START', job_info[0])

    tr = TargetRunner(queue, job_info[0], job_info[1])

    if tr.is_realtime():
        app.exec()
    else:
        tr.db_clock_start()

    logger.print('PROCESS DONE', job_info[0])
    queue.put('done')
    queue.close()
Exemplo n.º 12
0
    def order_event(self, result):
        # event from CpConclusion
        logger.print('ORDER EVENT', str(result))
        is_buy = result['order_type'] == '2'
        code = result['code']

        if result['flag'] == '4':   # Queued
            self.handle_queued(code, is_buy, result)
        elif result['flag'] == '1': # Traded
            self.handle_traded(code, is_buy, result)
        elif result['flag'] == '2': # Confirmed
            self.handle_edited(code, is_buy, result)
        else:
            # Is there anything to recover state
            logger.print('ORDER EVENT ERROR', str(result))

        """
Exemplo n.º 13
0
    def _td5339(self):
        orders = []
        while True:
            try:
                ret = self.obj.BlockRequest()
            except com_error:
                logger.error('TD5339 BlockRequest Error')
                return []

            if self.obj.GetDibStatus() != 0:
                logger.error('TD5339 failed')
                return []
            elif ret == 2 or ret == 3:
                logger.error('TD5339 communication failed')
                return []

            while ret == 4:
                if self.conn.request_left_count() <= 0:
                    time.sleep(self.conn.get_remain_time() / 1000)
                ret = self.obj.BlockRequest()
            
            count = self.obj.GetHeaderValue(5)

            for i in range(count):
                order = dict()
                order['number'] = self.obj.GetDataValue(1, i)
                order['prev'] = self.obj.GetDataValue(2, i) # 원주문 번호?
                order['code'] = self.obj.GetDataValue(3, i)
                order['name'] = self.obj.GetDataValue(4, i)
                order['desc'] = self.obj.GetDataValue(5, i)
                order['quantity'] = self.obj.GetDataValue(6, i)
                order['price'] = self.obj.GetDataValue(7, i)
                order['traded_quantity'] = self.obj.GetDataValue(8, i) # 체결수량
                order['credit_type'] = self.obj.GetDataValue(9, i) # 신용구분
                order['edit_available_quantity'] = self.obj.GetDataValue(11, i) #정정취소 가능수량
                order['is_buy'] = self.obj.GetDataValue(13, i) # 매매구분코드
                order['credit_date'] = self.obj.GetDataValue(17, i) # 대출일
                order['flag_describe'] = self.obj.GetDataValue(19, i) # 주문호가구분코드 내용
                order['flag'] = self.obj.GetDataValue(21, i)    # 주문호가구분코드
                logger.print('ORDER IN QUEUE', order)
                orders.append(order)
            if self.obj.Continue == False:
                break
        
        return orders
Exemplo n.º 14
0
    def received(self, datas):
        for g in self.graph_adder:
            g.received(datas)

        if self.next_elements is not None and not self.done:
            if self.past_highest == 0:
                if not self.get_past_record(datas[-1]['target']):
                    logger.print(datas[-1]['target'], 'no daily records')
                    self.done = True
                    return

            if not self.entered[0]:
                for d in datas:
                    if d['current_price'] > self.past_highest:
                        self.entered = (True, d['date'])
                        logger.print('entered')

                if self.entered[0]:
                    self.df = pd.DataFrame(datas)
                    self.df = self.df.set_index('date')
                    for g in self.graph_adder:
                        g.set_flag(datas[-1]['date'],
                                   'ENTERED:' + str(self.past_highest))
            else:
                self.df.append(datas, ignore_index=True)
                time_passed = datas[-1]['date'] - self.entered[1]
                if time_passed > timedelta(minutes=9):
                    if self.check_dataframe(self.df):
                        self.next_elements.received([{
                            'name':
                            self.__class__.__name__,
                            'target':
                            datas[-1]['target'],
                            'stream':
                            datas[-1]['stream'],
                            'date':
                            datas[-1]['date'],
                            'value':
                            True,
                            'price':
                            datas[-1]['current_price']
                        }])
                        for g in self.graph_adder:
                            g.set_flag(datas[-1]['date'], 'SUPRESSED')
                        self.done = True
Exemplo n.º 15
0
    def transaction(self, msg):
        # Investing 1 / 10 amount
        logger.print(str(msg))
        buy, code, price, tdate = msg['result'], msg['target'], msg['value'], msg['date']
        price = int(price)

        profit = 0
        if buy:
            self.account[code] = dict(price=price, date=tdate)
        else:
            profit = (price - self.account[code]['price']) / self.account[code]['price'] * 100.
            profit_d = {'date': self.date, 'code': code, 'buy_price': self.account[code]['price'], 'sell_price': price,
                        'profit_r': profit, 'buy_time': self.account[code]['date'], 'sell_time': tdate}
            if 'highest' in msg:
                profit_d['highest'] = msg['highest']

            for additional in self.additional_info:
                profit_d[additional[0]] = additional[1]
            self.profit_df = self.profit_df.append(profit_d, ignore_index = True)
Exemplo n.º 16
0
 def handle_queued(self, code, is_buy, result):
     logger.print('handle_queued', code, is_buy)
     if code in self.order_wait_queue:
         order_wait_item = self.order_wait_queue[code]
         if result['quantity'] == order_wait_item['quantity'] and is_buy == order_wait_item['order_type']:
             self.on_market_queue[code] = {'date': order_wait_item['date'], 
                                             'order_type': is_buy, 
                                             'order_number': result['order_number'],
                                             'quantity': result['quantity'], 
                                             'price': result['price'],
                                             'order_modify_type': OrderTransaction.NORMAL}
             self.order_wait_queue.pop(code, None)
             QTimer.singleShot(10000, self._check_on_market_queue)
         else:
             logger.error('wait queue and order event differ', 
                             result['quantity'], order_wait_item['quantity'],
                             is_buy, order_wait_item['order_type'])
     else:
         logger.error('code is not in order wait queue', code)
Exemplo n.º 17
0
    def make_order(self, code, price, quantity, is_buy):
        if not is_buy:
            if code in self.long_list:
                quantity = self.long_list[code]
            else:
                logger.error(code, 'is not int long_list')
                return

        record_make_order(code, price, quantity, is_buy)
        status, msg = self.order.process(code, quantity, self.account_num, 
                                        self.account_type, price, is_buy)

        if status != 0:
            logger.error(code, 'process error', code, price, quantity, is_buy, msg)
        else:
            logger.print('ORDER process', code, msg)
            self.order_wait_queue[code] = {
                'date': datetime.now(), 'order_type': is_buy, 
                'quantity': quantity, 'price': price}
            QTimer.singleShot(10000, self._check_order_wait_queue)
Exemplo n.º 18
0
    def process(self, code, quantity, account_num, account_type, price,
                is_buy):
        while self.conn.order_left_count() <= 0:
            logger.print("WAIT ORDER LEFT", code, quantity, is_buy, price)
            time.sleep(1)

        if quantity == 0:
            logger.print("Failed", code, quantity, is_buy, price)
        else:
            self.obj = win32com.client.Dispatch('CpTrade.CpTd0311')
            order_type = '2' if is_buy else '1'
            self.obj.SetInputValue(0, order_type)
            self.obj.SetInputValue(1, account_num)
            self.obj.SetInputValue(2, account_type)
            self.obj.SetInputValue(3, code)
            self.obj.SetInputValue(4, quantity)
            self.obj.SetInputValue(5, price)

            self.obj.BlockRequest()
            return self.obj.GetDibStatus(), self.obj.GetDibMsg1()

        return -1, 'Order Process Error(quantity=0)'
Exemplo n.º 19
0
 def _send_short(self):
     self.buy_hold = None
     self.current_stage = 0
     if self.next_element is not None:
         self.next_element.received([{
             'name':
             self.__class__.__name__,
             'target':
             self.latest_tick['target'],
             'stream':
             self.latest_tick['stream'],
             'date':
             self.latest_tick['date'],
             'value':
             False,
             'price':
             self.latest_tick['close_price'],
             'highest':
             self.highest_after_buy
         }])
         logger.print(self.latest_tick['date'], self.latest_tick['target'],
                      'SELL')
Exemplo n.º 20
0
    def received(self, datas):
        if self.next_elements is None:
            return

        result = True
        for d in datas:
            if d['cum_buy_volume'] <= d['cum_sell_volume']:
                result = False

        if self.last_result ^ result:
            logger.print(
                {
                    'name': self.__class__.__name__,
                    'type': 'Bool',
                    'value': str(result)
                }, d['time_with_sec'])
            self.next_elements.received([{
                'name': self.__class__.__name__,
                'target': datas[-1]['target'],
                'stream': datas[-1]['stream'],
                'date': datas[-1]['date'],
                'value': result
            }])
            self.last_result = result
Exemplo n.º 21
0
    def set_target(self, target):
        code = target
        if ':' in target:
            code = target.split(':')[1]
        self.target_code = code
        stock = MongoClient(db.HOME_MONGO_ADDRESS)['stock']

        cursor = stock[code].find({'date': {'$gte':self.from_datetime, '$lte': self.until_datetime}})
        self.data = list(cursor)
        """
        i = 0
        while True:
            cursor = stock[code].find({'date': {'$gte':self.from_datetime, '$lte': self.until_datetime}}).skip(i * 500).limit(500)
            self.data.extend(list(cursor))
            #print(len(self.data))
            if cursor.count(with_limit_and_skip=True) < 500:
                break
            i += 1
        """

        #logger.print(target, 'Length', len(self.data))
        if len(self.data) > 0 and self.check_whole_data:
            df = pd.DataFrame(self.data)

            if self.save_to_excel:
                df.to_excel(code + '_from_db.xlsx')

            market = df['20']
            has_enough_market_type = len(market[market == 49]) > 10 and len(market[market == 50]) > 100 and len(market[market == 53]) > 10
            start_time = df['3']
            has_time_scope = len(start_time[start_time < 900]) > 10 and len(start_time[start_time > 1520]) > 10
            if has_enough_market_type and has_time_scope:
                pass
            else:
                self.data = []
                logger.print('Abnormal detected', target)
Exemplo n.º 22
0
    def _handle_data(self, datas):
        if self.done: return

        for d in datas:
            self.latest_tick = d
            if (d['date'].hour >= stock_time.MARKET_CLOSE_HOUR
                    and d['date'].minute >= stock_time.STOCK_COVERING_MINUTE
                    and self.buy_hold is not None):
                self._send_short()
                for g in self.graph_adder:
                    g.set_flag(d['date'], 'SELL')
                self.done = True
                break
            elif (d['date'].hour >= stock_time.STOCK_COVERING_MINUTE
                  and d['date'].minute >= stock_time.STOCK_BUY_BLOCK_MINUTE
                  and self.buy_hold is None):
                self.done = True
                break

            #if self.open_price == 0:
            #    self.open_price = d['start_price']

            self.price_array = np.append(self.price_array, [d['close_price']])
            self.date_array = np.append(self.date_array, [d['date']])

            if len(self.price_array) < 10:
                self.moving_average = np.append(self.moving_average,
                                                [self.price_array.mean()])
                continue
            else:
                self.moving_average = np.append(
                    self.moving_average, [self.price_array[-10:].mean()])

            if (self.buy_hold is not None and d['date'] - self.buy_hold <
                    timedelta(minutes=stock_time.BUY_HOLD_DURATION_MINUTE)):
                continue
            #elif 'VI' in d and d['VI']:
            #    continue

            reverse_prices = self._get_reversed(self.moving_average)
            peaks_top, prominences_top = self._calculate(self.moving_average)
            peaks_bottom, prominences_bottom = self._calculate(reverse_prices)

            trend_top = self._find_trend(self.moving_average, peaks_top,
                                         prominences_top, True)
            trend_bottom = self._find_trend(self.moving_average, peaks_bottom,
                                            prominences_bottom, False)

            cum_sum = (d['cum_buy_volume'] + d['cum_sell_volume']) * 0.1
            volume_trend = d['cum_buy_volume'] > d['cum_sell_volume'] + cum_sum
            #price_exceed = (d['close_price'] - self.open_price) / self.open_price * 100. > 15.
            bottom = trend_bottom[0] and trend_bottom[1]
            top = trend_top[0] and trend_top[1]

            for g in self.graph_adder:
                for p_top in peaks_top:
                    g.set_circle_flag(self.date_array[p_top],
                                      self.moving_average[p_top], True)
                for p_bottom in peaks_bottom:
                    g.set_circle_flag(self.date_array[p_bottom],
                                      self.moving_average[p_bottom], False)

            if self.current_stage == 0:
                if bottom and not top and volume_trend:  # and not price_exceed:
                    self.current_stage = 1
                    if len(peaks_top) == 0:
                        continue
                    self.buy_margin_price[0] = self.moving_average[
                        peaks_top[-1]]
                    self.buy_margin_price[1] = self.moving_average[peaks_top[
                        -2]] if len(peaks_top) > 1 else self.moving_average[
                            peaks_top[-1]]
            elif self.current_stage == 1:
                lowest_price, highest_price = 0, 0
                if volume_trend and bottom:
                    if len(self.moving_average) > 50:
                        lowest_price = self.moving_average[:-50].min()
                        highest_price = self.moving_average[:-50].max()
                    else:
                        lowest_price = self.moving_average.min()
                        highest_price = self.moving_average.max()
                    risk = float("{0:.2f}".format(
                        (highest_price - lowest_price) / lowest_price * 100.))
                    is_cross_margin = self.moving_average[
                        -1] > self.buy_margin_price[0] or self.moving_average[
                            -1] > self.buy_margin_price[1]
                    #over_price = (d['close_price'] - self.open_price) / self.open_price * 100 > 10. # TODO : double check with price_exceed?
                    if self.buy_hold is None and is_cross_margin and risk < 13.:  #and not over_price:
                        logger.print(d['date'], d['target'], 'BUY')
                        self.buy_hold = d['date']
                        if self.next_element is not None:
                            self.next_element.received([{
                                'name':
                                self.__class__.__name__,
                                'target':
                                d['target'],
                                'stream':
                                d['stream'],
                                'date':
                                d['date'],
                                'value':
                                True,
                                'price':
                                d['close_price'],
                                'risk':
                                risk
                            }])
                            self.current_stage = 2
                            self.highest_after_buy = d['close_price']
                        for g in self.graph_adder:
                            g.set_flag(d['date'], 'BUY')
                else:
                    self.current_stage = 0
            elif self.current_stage == 2:
                if d['highest_price'] > self.highest_after_buy:
                    self.highest_after_buy = d['highest_price']
                # add condition: current price is under -1% than highest
                if (not volume_trend
                        or not bottom) and self.buy_hold is not None:

                    for g in self.graph_adder:
                        g.set_flag(d['date'], 'SELL')
                    self._send_short()
Exemplo n.º 23
0
 def subscribe(self, filter_callback):
     handler = win32com.client.WithEvents(self.obj, _CpEvent)
     self.obj.SetInputValue(0, self.code)
     handler.set_params(self.obj, self.code, filter_callback)
     self.obj.Subscribe()
     logger.print('START Subscribe', self.code)