Example #1
0
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.timer2 = QTimer(self)
        self.timer2.start(1000 *10)
        self.timer2.timeout.connect(self.timeout2)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)

        self.load_buy_sell_list()
Example #2
0
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)
Example #3
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)
Example #4
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.timer2 = QTimer(self)
        self.timer2.start(1000 *10)
        self.timer2.timeout.connect(self.timeout2)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)

        self.load_buy_sell_list()

    def trade_stocks(self):
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt')
        sell_list = f.readlines()
        f.close()

        # account
        account = self.comboBox.currentText()

        # buy list
        for row_data in buy_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[2]
            code = split_row_data[1]
            num = split_row_data[3]
            price = split_row_data[4]

            if split_row_data[-1].rstrip() == '매수전':
                self.kiwoom.send_order("send_order_req", "0101", account, 1, code, num, price, hoga_lookup[hoga], "")

        # sell list
        for row_data in sell_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[2]
            code = split_row_data[1]
            num = split_row_data[3]
            price = split_row_data[4]

            if split_row_data[-1].rstrip() == '매도전':
                self.kiwoom.send_order("send_order_req", "0101", account, 2, code, num, price, hoga_lookup[hoga], "")

        # buy list
        for i, row_data in enumerate(buy_list):
            buy_list[i] = buy_list[i].replace("매수전", "주문완료")

        # file update
        f = open("buy_list.txt", 'wt')
        for row_data in buy_list:
            f.write(row_data)
        f.close()

        # sell list
        for i, row_data in enumerate(sell_list):
            sell_list[i] = sell_list[i].replace("매도전", "주문완료")

        # file update
        f = open("sell_list.txt", 'wt')
        for row_data in sell_list:
            f.write(row_data)
        f.close()

    def load_buy_sell_list(self):
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt')
        sell_list = f.readlines()
        f.close()

        row_count = len(buy_list) + len(sell_list)
        self.tableWidget_4.setRowCount(row_count)

        # buy list
        for j in range(len(buy_list)):
            row_data = buy_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(split_row_data[1].rsplit())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_4.setItem(j, i, item)

        # sell list
        for j in range(len(sell_list)):
            row_data = sell_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(split_row_data[1].rstrip())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_4.setItem(len(buy_list) + j, i, item)

        self.tableWidget_4.resizeRowsToContents()

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account, order_type_lookup[order_type], code, num, price, hoga_lookup[hoga], "")

    def timeout(self):
        market_start_time = QTime(9, 0, 0)
        current_time = QTime.currentTime()

        if current_time > market_start_time and self.trade_stocks_done is False:
            self.trade_stocks()
            self.trade_stocks_done = True

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i - 1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
Example #5
0
class TrTrader():
    def __init__(self, simctrl_instance=None):
        self.ext_command_last_excution_time_ = datetime.now(
        )  # last execution set to __init__ time initiation
        if USE_SIMULATOR:
            self.km = Simulator(simctrl_instance)
        else:
            self.km = Kiwoom()
        if not self.km.connect_status:
            tl_print("System exits")
            sys.exit()
        self.bounds_table = bounds_prep()
        self.prev_mbf_exists = os.path.exists(MASTER_BOOK_FILE)
        self.trtrade_list = pd.DataFrame(
            columns=['code', 'amount', 'buy_sell', 'note'])
        self.master_book_initiator(START_CASH, replace=CREATE_NEW_MASTER_BOOK)
        if not USE_SIMULATOR:
            self.master_book_integrity_checker()

    def close_(self):
        self.write_master_book_to_Excel(self.master_book)
        self.status_print(to_file=True)
        if not USE_SIMULATOR:
            self.status_print(to_file=False)  # print to screen too

    def __del__(self):
        del self.km

    def run_(self):
        self.execute_external_control_command(
        )  # web-based control through AWS
        cash = self.trendtrading_mainlogic(
        )  # returns cash amount if all trtrade_list buy_sells are executed
        self.load_external_trade_list(cash)
        trtrade_list_yetitems = self.trtrade_list.loc[self.trtrade_list['note']
                                                      == 'yet']
        if len(trtrade_list_yetitems) == 0:
            if PRINT_TO_SCREEN:
                tl_print(
                    time.strftime("t%H:%M:%S")
                )  #, end="\r")  # Exception for trade_log_print (tl_print)
                # print('.', end='')
            if USE_SIMULATOR:
                return False
        else:
            self.trade_stocks()
            self.status_print(to_file=False)  # print to screen too
            if USE_SIMULATOR:
                return True
        self.status_print(to_file=True)

    def load_external_trade_list(self, cash):
        # if a file that contains a list of stocks to be traded exists, load it
        if os.path.exists(EXTERNAL_LIST_FILE):
            el = TrTrader.read_external_buysell_list()
            self.external_list_prep(cash, el)

        # when USE_SIMULATOR, each run_() run will load external list created at SimController
        if USE_SIMULATOR:
            self.external_list_prep(cash, self.km.simctrl.ext_list_gen())

    def external_list_prep(self, cash, el):
        bk = self.km.get_account_stock_list(ACCOUNT_NO)
        for i in el.index:
            if el.at[i, 'code'] in TRENDTRADE_EXCEPT_LIST:
                tl_print(
                    "*** WARNING: External buysell list contains item in TRENDTRADE_EXCEPT_LIST: ",
                    el.at[i, 'code'], " - this item ignored")
                el = el.drop(i)
                continue

            cprice = self.km.get_price(el.at[i, 'code'])
            if cprice == 0:
                tl_print(
                    "*** WARNING: External list contains item with zero current price: ",
                    el.at[i, 'code'], " - this item ignored")
                el = el.drop(i)
                continue

            if el.at[i, 'buy_sell'] == 'buy':
                if el.at[i, 'code'] in list(bk['code']):
                    tl_print(
                        "*** WARNING: External list contains item in current trtrading list: ",
                        el.at[i, 'code'], " - this item ignored")
                    el = el.drop(i)
                    continue
                if el.at[i, 'amount'] == 0:
                    el.at[i, 'amount'] = int(round(TICKET_SIZE / cprice))
                    tl_print(
                        "*** External list contains item with buy quantity set to zero: ",
                        el.at[i, 'code'], " - buy quanity set to TICKET_SIZE")
                ticket = int(
                    round(cprice * el.at[i, 'amount'] *
                          self.tax_fee_adjustment('buy')))
                if cash > ticket * MIN_CASH_FOR_PURCHASE_RATE:
                    cash = cash - ticket
                else:
                    tl_print(
                        "Exception: Cash is not enough for external list purchase: "
                        + el.at[i, 'code'])
                    raise Exception()
            else:  # 'sell'
                if el.at[i, 'code'] not in list(bk['code']):
                    tl_print(
                        "*** WARNING: External list contains sell item not in current trtrading list: ",
                        el.at[i, 'code'], " - this item ignored")
                    continue
                ci = bk.loc[bk['code'] == el.at[i, 'code']]
                if el.at[i, 'amount'] == 0:
                    el.at[i, 'amount'] = int(ci['nshares'])
                    tl_print(
                        "*** External list contains item with sell quantity set to zero: ",
                        el.at[i, 'code'], " - sell quanity set to max")
                elif el.at[i, 'amount'] > int(ci['nshares']):
                    el.at[i, 'amount'] = int(ci['nshares'])
                    tl_print(
                        "*** WARNING: External list contains item with sell quantity exceeding current quantity: ",
                        el.at[i, 'code'], " - sell quanity set to max")
                else:
                    pass
                ticket = int(
                    round(cprice * el.at[i, 'amount'] *
                          self.tax_fee_adjustment('sell')))
                cash = cash + ticket

        if len(el) > 0:
            tl_print('External buy_sell list loaded')
            self.trtrade_list = self.trtrade_list.append(el)
            self.trtrade_list = self.trtrade_list.reset_index(drop=True)

    def trade_stocks(self):
        ##################################################
        # MAY NEED TO MODIFY TO SELL FIRST AND THEN BUY
        bs_lookup = {'buy': 1, 'sell': 2}
        self.tr_data = []
        self.tr_data_res_ = []
        for i in self.trtrade_list.index:
            if self.trtrade_list["note"][
                    i] == 'yet':  # or self.trtrade_list["note"][i] == 'failed': ############################### For failed, re running of tr-mainlogic would result in adding the same item
                res = self.km.send_order(
                    "send_order_req", "0101", ACCOUNT_NO,
                    bs_lookup[self.trtrade_list["buy_sell"][i]],
                    self.trtrade_list["code"][i],
                    self.trtrade_list["amount"][i], 0, '03',
                    "")  # trade in market price, price = 0, hoga = '3'

                if res[0] == 0 and res[1] != "":  # success
                    self.trtrade_list.at[i, "note"] = 'ordered'
                    self._write_transaction_to_master_book(
                        self.km.chejan_finish_data[0],
                        self.km.chejan_finish_data[1],
                        self.km.chejan_finish_data[2],
                        self.km.chejan_finish_data[3],
                        self.km.chejan_finish_data[4],
                        self.km.chejan_finish_data[5])
                    self.km.chejan_finish_data.append(self.tr_data_res_)
                    self.tr_data.append(self.km.chejan_finish_data)
                    self.km.chejan_finish_data = []
                    # self.tr_data = [stock_code, stock_name, buy_sell, avg_price, int(pv), tr_time, [invtotal, ret]]
                else:
                    tl_print("--- Error in order processing: ",
                             self.trtrade_list['code'][i])
                    self.trtrade_list.at[i, "note"] = 'failed'

    def trendtrading_mainlogic(self):
        # Trend trading logic
        # [step 0] for active set copy, do the following
        mb_active = self.master_book.loc[self.master_book['active']]
        cash = self.master_book.at[
            self.master_book.index[-1],
            'cash']  # to be cash after the trtrade_list generated by a trendtrading_mainlogic run is excuted
        book_cash = cash  # cash to be written at the last line of master_book
        if USE_SIMULATOR:
            tr_time = self.km.simctrl.sim_time
        else:
            tr_time = time.ctime()

        # [step 1] update cprice, cvalue, retrate
        for i in mb_active.index:
            updated_price = self.km.get_price(mb_active.at[i, 'code'])
            updated_value = int(
                round(updated_price * mb_active.at[i, 'nshares'] *
                      self.tax_fee_adjustment('sell')))
            updated_rr = round(updated_value / mb_active.at[i, 'invtotal'] - 1,
                               4)  # return rate
            mb_active.at[i, 'cprice'] = updated_price
            mb_active.at[i, 'cvalue'] = updated_value
            mb_active.at[i, 'retrate'] = updated_rr

            # [step 2] for dec_made == SUSPEND or EXCEPT, check if rr is back up to LB
            # then dec_made = released, update dec_time
            # otherwise, leave it as is
            if mb_active.at[i, 'dec_made'] == "SUSPEND" or mb_active.at[
                    i, 'dec_made'] == "EXCEPT":
                if updated_rr >= mb_active.at[i, 'LB']:
                    mb_active.at[i, 'dec_made'] = "released"
                    mb_active.at[i, 'dec_time'] = tr_time
                    self.master_book.loc[i, 'active'] = False
                    new_line = mb_active.loc[mb_active.index == i]
                    new_line.at[i, 'cash'] = book_cash
                    new_line.index = [len(self.master_book)]
                    self.master_book = self.master_book.append(new_line)
        # [step 3] for dec_made != SUSPEND and != "EXCEPT": compare rr with LLB, LB, UB
            else:  # if mb_active.at[i, 'dec_made'] != "SUSPEND" and mb_active.at[i, 'dec_made'] != "EXCEPT":
                # if hits LLB, suspend trading until it reaches LB: dec_made = SUSPEND, update dec_time
                if updated_rr <= mb_active.at[i, 'LLB']:
                    mb_active.at[i, 'dec_made'] = "SUSPEND"
                    mb_active.at[i, 'dec_time'] = tr_time
                    self.master_book.loc[i, 'active'] = False
                    new_line = mb_active.loc[mb_active.index == i]
                    new_line.at[i, 'cash'] = book_cash
                    new_line.index = [len(self.master_book)]
                    self.master_book = self.master_book.append(new_line)

                # if in between LLB and LB, sell (at loss): add this item to the trtrade_list (sell), code and quantity, DO NOT CHANGE MASTER BOOK
                else:
                    if updated_rr <= mb_active.at[i, 'LB']:
                        self.trtrade_list.loc[len(self.trtrade_list)] = [
                            self.master_book.at[i, 'code'],
                            int(self.master_book.at[i, 'nshares']), 'sell',
                            'yet'
                        ]
                        tl_print("Situation 1 - lower than LB: ",
                                 self.master_book.at[i, 'code'],
                                 " sell")  #########################
                        cash = cash + updated_value
                # if in between LB and UB: hold
                    elif updated_rr < mb_active.at[i, 'UB']:
                        pass
                # if hits UB:
                    else:
                        # elif no_repurchase = MAX_ELEVATION: add this item to the trade_list (sell), DO NOT CHANGE MASTER BOOK
                        nr = mb_active.at[i, 'nreinv']
                        if nr == MAX_ELEVATION:
                            self.trtrade_list.loc[len(self.trtrade_list)] = [
                                self.master_book.at[i, 'code'],
                                int(self.master_book.at[i, 'nshares']), 'sell',
                                'yet'
                            ]
                            tl_print("Situation 2 - more than MAX_ELEVATION: ",
                                     self.master_book.at[i, 'code'],
                                     " sell")  ##########################
                            cash = cash + updated_value
                        else:
                            # check cash,
                            # if cash > MIN_CASH_FOR_PURCHASE and no_repurchase < MAX_REINVESTMENT: add this item to trade_list (buy), DO NOT CHANGE MASTER BOOK
                            if cash > MIN_CASH_FOR_PURCHASE and nr < MAX_REINVESTMENT:
                                self.trtrade_list.loc[len(
                                    self.trtrade_list)] = [
                                        self.master_book.at[i, 'code'],
                                        int(round(TICKET_SIZE /
                                                  updated_price)), 'buy', 'yet'
                                    ]
                                tl_print("Situation 3 - higher than UB: ",
                                         self.master_book.at[i, 'code'],
                                         " buy")  ##########################
                                cash = cash - TICKET_SIZE
                            # else elevate bounds 1 steps, and update no_repurchase, dec_made = "bd_elev" and dec_time
                            else:
                                mb_active.at[i, 'nreinv'] = nr + 1
                                [LLB, LB, UB] = self.bounds(nr + 1)
                                mb_active.at[i, 'LLB'] = LLB
                                mb_active.at[i, 'LB'] = LB
                                mb_active.at[i, 'UB'] = UB
                                mb_active.at[i, 'dec_made'] = 'bd_elev'
                                mb_active.at[i, 'dec_time'] = tr_time
                                self.master_book.loc[i, 'active'] = False
                                new_line = mb_active.loc[mb_active.index == i]
                                new_line.at[i, 'cash'] = book_cash
                                new_line.index = [len(self.master_book)]
                                self.master_book = self.master_book.append(
                                    new_line)
        return cash

    def master_book_integrity_checker(self):
        bk = self.km.get_account_stock_list(ACCOUNT_NO)
        for exception_code in TRENDTRADE_EXCEPT_LIST:
            bk = bk[bk['code'] != exception_code]
        bk = bk.reset_index(drop=True)
        ch = int(self.km.get_cash(ACCOUNT_NO))
        tl_print('Cash in Kiwoom Account is: ', format(ch, ','))

        if self.prev_mbf_exists == False or CREATE_NEW_MASTER_BOOK == True:
            if ch < START_CASH - bk['invtotal'].sum(
            ) * self.tax_fee_adjustment('buy'):
                tl_print('Exception: INSUFFICIENT CASH TO START TREND TRADING')
                raise Exception()
            entries = pd.DataFrame(columns=self.master_book.columns)
            entries[[
                'code', 'name', 'cprice', 'nshares', 'invtotal', 'cvalue',
                'retrate'
            ]] = bk[[
                'code', 'name', 'cprice', 'nshares', 'invtotal', 'cvalue',
                'retrate'
            ]]
            entries['invtotal'] = round(entries['invtotal'] *
                                        self.tax_fee_adjustment('buy'))
            entries['cvalue'] = round(entries['cvalue'] *
                                      self.tax_fee_adjustment('sell'))
            entries = entries.astype({'invtotal': 'int', 'cvalue': 'int'})
            entries['ret'] = 0
            entries['retrate'] = round(
                (entries['cvalue'] - entries['invtotal']) /
                entries['invtotal'], 4)
            entries['init_invtime'] = entries['dec_time'] = time.ctime()
            entries['dec_made'] = 'loaded'
            entries['active'] = True
            for i in entries.index:
                res = self.nreinv_find(entries.at[i, 'retrate'])
                if res[0] == -1:
                    entries.at[i, 'dec_made'] = 'EXCEPT'
                    tl_print(' - ', entries.at[i, 'code'],
                             entries.at[i, 'name'], ' > EXCEPT')
                entries.at[i, 'nreinv'] = nr = res[1]
                [LLB, LB, UB] = self.bounds(nr)
                entries.at[i, 'LLB'] = LLB
                entries.at[i, 'LB'] = LB
                entries.at[i, 'UB'] = UB
                if i == 0:
                    entries.at[i, 'cash'] = int(START_CASH -
                                                entries.at[i, 'invtotal'])
                else:
                    entries.at[i, 'cash'] = int(entries.at[i - 1, 'cash'] -
                                                entries.at[i, 'invtotal'])
            self.master_book = self.master_book.append(entries)
            self.master_book = self.master_book.reset_index(drop=True)
            tl_print(
                '[Initiation success]: Existing stock list from Kiwoom API loaded into master_book'
            )

        else:
            #############################################
            # Loading existing book
            # master_book active items should match bk items
            mb_cash = self.master_book.at[len(self.master_book) - 1, 'cash']
            if mb_cash > ch:
                tl_print(
                    "Exception: Master_book loading error - cash balance insufficient"
                )
                raise Exception()
            mb_active = self.master_book.loc[self.master_book[
                'active']]  # selected subset of DataFrame is already a deep copy of original DataFrame
            if len(mb_active) != len(bk):
                tl_print("Exception: Master_Book integrity check: error (1)")
                raise Exception(
                )  # this error could occur when releasing from and adding to TRENDTRADE_EXCEPT_LIST
            for i in bk.index:
                mt = mb_active[mb_active['code'] == bk.at[i, 'code']]
                if len(mt) != 1:
                    tl_print(
                        "Exception: Master_Book integrity check: error (2)")
                    raise Exception()
                l = list(mt.index)[0]
                if mt.at[l, 'nshares'] != bk.at[i, 'nshares']:
                    tl_print(
                        "Exception: Master_Book integrity check: error (3)")
                    raise Exception()
                if (mt.at[l, 'invtotal'] -
                        bk.at[i, 'invtotal'] * self.tax_fee_adjustment('buy')
                    ) / mt.at[l, 'invtotal'] > 0.01:
                    tl_print(
                        "Exception: Master_Book integrity check: error (4)")
                    raise Exception()
            tl_print(
                '[Initiation success]: Existing stock list from Kiwoom API matches with master_book'
            )

    def master_book_initiator(self, initial_cash_amount, replace=False):
        if self.prev_mbf_exists and not replace:
            # tl_print("Using existing master book - master book file exists")
            pass

        else:
            if self.prev_mbf_exists and replace:
                t = time.strftime("_%Y%m%d_%H%M%S")
                n = MASTER_BOOK_BACKUP_FILE[:-5]
                os.rename(MASTER_BOOK_FILE, n + t + '.xlsx')

            self.prev_mbf_exists = False
            mb = xlsxwriter.Workbook(MASTER_BOOK_FILE)
            mbws = mb.add_worksheet()
            mbws.write('A1', 'code')
            mbws.write('B1', 'name')
            mbws.write(
                'C1',
                'cprice')  # price at the time of the decision, current_price
            mbws.write('D1', 'nshares')  # number of shares
            mbws.write('E1', 'nreinv')  # number of reinvestements
            mbws.write('F1', 'LLB')  # Limit Lower Bound
            mbws.write('G1', 'LB')
            mbws.write('H1', 'UB')
            mbws.write('I1',
                       'invtotal')  # invested total amount after entry fee
            mbws.write(
                'J1', 'cvalue'
            )  # value at the time of the decision (after tax and exit fee) current_value
            mbws.write('K1', 'retrate')  # return_rate
            mbws.write(
                'L1', 'ret'
            )  # return resulted due to the decision in the current line
            mbws.write('M1', 'init_invtime')
            mbws.write(
                'N1', 'dec_made')  # decision that resulted in the current line
            mbws.write('O1', 'dec_time')
            mbws.write(
                'P1', 'active'
            )  # True: for currently holding stocks, False: for record
            mbws.write('Q1', 'cash')  # d+2 cash after all tax and fee

            mbws.write('A2', '-')
            mbws.write('B2', 'init')
            mbws.write('C2', 0)
            mbws.write('D2', 0)
            mbws.write('E2', 0)
            mbws.write('F2', 0)
            mbws.write('G2', 0)
            mbws.write('H2', 0)
            mbws.write('I2', 0)
            mbws.write('J2', 0)
            mbws.write('K2', 0)
            mbws.write('L2', 0)
            mbws.write('M2', time.ctime())
            mbws.write('N2', '-')
            mbws.write('O2', time.ctime())
            mbws.write('P2', False)
            mbws.write('Q2', initial_cash_amount)
            mb.close()

        self.master_book = self.read_master_book_from_Excel()

    def read_master_book_from_Excel(self):
        mb_converters = {
            'code': str,
            'name': str,
            'cprice': int,
            'nshares': int,
            'nreinv': int,
            'LLB': float,
            'LB': float,
            'UB': float,
            'invtotal': int,
            'cvalue': int,
            'retrate': float,
            'ret': int,
            'init_invtime': str,
            'dec_made': str,
            'dec_time': str,
            'active': bool,
            'cash': int
        }

        master_book = pd.read_excel(MASTER_BOOK_FILE,
                                    index_col=None,
                                    converters=mb_converters)
        master_book['init_invtime'] = pd.to_datetime(
            master_book['init_invtime'])
        master_book['dec_time'] = pd.to_datetime(master_book['dec_time'])

        return master_book

    @staticmethod
    def read_external_buysell_list():
        el_converters = {
            'code': str,
            'amount': int,
            'buy_sell': str,
            'note': str
        }
        el = pd.read_excel(EXTERNAL_LIST_FILE,
                           index_col=None,
                           converters=el_converters)

        t = time.strftime("_%Y%m%d_%H%M%S")
        n = EXTERNAL_LIST_BACKUP_FILE[:-5]
        os.rename(EXTERNAL_LIST_FILE, n + t + '.xlsx')

        return el

    def write_master_book_to_Excel(self, master_book):
        master_book.to_excel(MASTER_BOOK_FILE, index=False)

    def _write_transaction_to_master_book(self, code, name, buy_sell, price,
                                          quantity, tr_time):
        # this function is to be used only after SendOrder success
        mb_active = self.master_book.loc[self.master_book["active"]]
        active_line = mb_active[mb_active['code'] == code]

        if buy_sell == 'buy':
            if len(active_line) == 0:
                new_line = pd.DataFrame(columns=self.master_book.columns)
                new_line.at[0, 'code'] = code
                new_line.at[0, 'name'] = name
                new_line.at[0, 'cprice'] = price
                new_line.at[0, 'nshares'] = quantity
                new_line.at[0, 'nreinv'] = nr = 0
                [LLB, LB, UB] = self.bounds(nr)
                new_line.at[0, 'LLB'] = LLB
                new_line.at[0, 'LB'] = LB
                new_line.at[0, 'UB'] = UB
                new_line.at[0, 'invtotal'] = v1 = int(
                    round(price * quantity * self.tax_fee_adjustment('buy')))
                new_line.at[0, 'cvalue'] = v2 = int(
                    round(price * quantity * self.tax_fee_adjustment('sell')))
                new_line.at[0, 'retrate'] = round((v2 - v1) / v1, 4)
                new_line.at[0, 'ret'] = 0
                new_line.at[0, 'init_invtime'] = tr_time
                new_line.at[0, 'dec_made'] = 'new_ent'
                new_line.at[0, 'dec_time'] = tr_time
                new_line.at[0, 'active'] = True
                new_line.at[0, 'cash'] = ch = self.master_book.at[
                    len(self.master_book) - 1, 'cash'] - v1

            elif len(active_line) == 1:
                idx = list(active_line.index)[0]
                self.master_book.at[idx, 'active'] = False
                new_line = active_line
                new_line.at[idx, 'cprice'] = price  # price update
                new_line.at[idx, 'nshares'] = ns = new_line.at[
                    idx, 'nshares'] + quantity  # repurchase
                new_line.at[idx,
                            'nreinv'] = nr = new_line.at[idx, 'nreinv'] + 1
                if nr > MAX_REINVESTMENT:
                    tl_print(
                        "Exception: Do not attmpt to purchase over MAX_ELEVATION"
                    )
                    raise Exception()
                [LLB, LB, UB] = self.bounds(nr)
                new_line.at[idx, 'LLB'] = LLB
                new_line.at[idx, 'LB'] = LB
                new_line.at[idx, 'UB'] = UB
                repv = int(
                    round(price * quantity * self.tax_fee_adjustment('buy')))
                new_line.at[idx,
                            'invtotal'] = v1 = new_line.at[idx,
                                                           'invtotal'] + repv
                new_line.at[idx, 'cvalue'] = v2 = int(
                    round((price * ns) * self.tax_fee_adjustment('sell')))
                new_line.at[idx, 'retrate'] = round((v2 - v1) / v1, 4)
                new_line.at[idx, 'ret'] = 0
                # new_line.at[0, 'init_invtime'] = tr_time # does not change
                new_line.at[idx, 'dec_made'] = 'reinv'
                new_line.at[idx, 'dec_time'] = tr_time  # update time
                new_line.at[idx, 'active'] = True
                new_line.at[idx, 'cash'] = ch = self.master_book.at[
                    len(self.master_book) - 1, 'cash'] - repv

            else:
                tl_print("Exception: ERROR in Master_Book Integrity - buy")
                raise Exception()

        else:  # buy_sell == 'sell':
            if len(active_line) == 1:
                idx = list(active_line.index)[0]
                self.master_book.at[idx, 'active'] = False
                new_line = active_line
                new_line.at[idx, 'cprice'] = price  # price update
                original_quantity = new_line.at[idx, 'nshares']
                new_line.at[
                    idx,
                    'nshares'] = remained_quantity = original_quantity - quantity
                avg_price = new_line.at[idx, 'invtotal'] / original_quantity
                new_line.at[idx,
                            'invtotal'] = v1 = avg_price * remained_quantity
                new_line.at[idx, 'cvalue'] = v2 = int(
                    round(price * remained_quantity *
                          self.tax_fee_adjustment('sell')))
                if v1 != 0:  # remained_quantity is not zero
                    new_line.at[idx, 'retrate'] = round((v2 - v1) / v1, 4)
                else:
                    new_line.at[idx, 'retrate'] = 0
                v3 = int(
                    round(price * quantity * self.tax_fee_adjustment('sell')))
                new_line.at[idx, 'ret'] = v3 - avg_price * quantity
                if remained_quantity == 0:
                    new_line.at[idx, 'dec_made'] = 'a_sold'
                    new_line.at[idx, 'active'] = False
                    #################################################################
                    # tr_data saves results only when a_sold
                    self.tr_data_res_ = [
                        self.master_book.at[idx, 'invtotal'],
                        new_line.at[idx, 'ret']
                    ]
                else:
                    new_line.at[idx, 'dec_made'] = 'p_sold'
                    new_line.at[idx, 'active'] = True
                new_line.at[idx, 'dec_time'] = tr_time
                new_line.at[idx, 'cash'] = ch = self.master_book.at[
                    len(self.master_book) - 1, 'cash'] + v3
            else:
                tl_print("Exception: ERROR in Master_Book Integrity - sell")
                raise Exception()

        new_line.index = [len(self.master_book)]
        self.master_book = self.master_book.append(new_line)

    def bounds(self, nr):  # nr = number of repurchase
        UB = round(self.bounds_table.at['UB', nr], 4)
        LB = round(self.bounds_table.at['LB', nr], 4)
        LLB = round(self.bounds_table.at['LLB', nr], 4)
        return [LLB, LB, UB]

    def nreinv_find(self, rr):
        res = [0, 0]
        if rr <= self.bounds_table.at['LLB', 0]:
            # raise Exception("Current return rate is even lower than LLB for initial investment")
            # print("Return rate is even lower than LLB for initial investment")
            res[0] = -1
        elif rr <= self.bounds_table.at['LB', 0]:
            # raise Exception("Current return rate is even lower than LB for initial investment")
            # print("Return rate is even lower than LB for initial investment")
            res[0] = -1
        else:
            pass

        for i in self.bounds_table.columns:
            if rr <= self.bounds_table.at['LB', i]:
                res[1] = max(i - 1, 0)
                return res
        res[1] = MAX_ELEVATION
        return res

    def tax_fee_adjustment(self, buy_sell):
        if buy_sell == 'buy':
            return 1 + FEE_RATE  # when buying, you pay additional cash for fee
        else:  # buy_sell == 'sell':
            return 1 - (FEE_RATE + TAX_RATE
                        )  # when selling, your cash is dedcuted by tax and fee

    def execute_external_control_command(self):
        [command_time, ext_command] = self.read_external_command()
        if ext_command != '':
            tl_print('External command [' + ext_command +
                     '] recognized at time: ' +
                     datetime.now().strftime("%Y%m%d %H:%M:%S") +
                     ' (command created at: ' + command_time + ')')
            if ext_command == 'suspend':
                tl_print(
                    "*****************************************************")
                tl_print(
                    "PROCESS SUSPENDED PER THE EXTERNAL COMMAND: [suspend]")
                tl_print(
                    "*****************************************************")
                while 1:
                    # tl_print("System suspended - waiting for", EXT_COMM_SUSPEND_SLEEPING_TIME, "seconds until recheck")
                    time.sleep(EXT_COMM_SUSPEND_SLEEPING_TIME)
                    [command_time, ext_command] = self.read_external_command()
                    if ext_command == 'resume':
                        tl_print('External command [' + ext_command +
                                 '] recognized at time: ' +
                                 self.ext_command_last_excution_time_.strftime(
                                     "%Y%m%d %H:%M:%S") +
                                 ' (command created at: ' + command_time + ')')
                        tl_print(
                            "*****************************************************"
                        )
                        tl_print(
                            "PROCESS RESUMED PER THE EXTERNAL COMMAND: [resume]"
                        )
                        tl_print(
                            "*****************************************************"
                        )
                        break
                    elif ext_command == 'stop':
                        tl_print('External command [' + ext_command +
                                 '] recognized at time: ' +
                                 self.ext_command_last_excution_time_.strftime(
                                     "%Y%m%d %H:%M:%S") +
                                 ' (command created at: ' + command_time + ')')
                        break
                    elif ext_command == 'ping':
                        tl_print("ping > trtrader is suspended")
            elif ext_command == 'resume':
                tl_print(
                    "[resume] command not executed in suspend status is ignored"
                )
            elif ext_command == 'ping':
                tl_print("ping > trtrader is running")

            if ext_command == 'stop':
                tl_print(
                    "*****************************************************")
                tl_print("PROCESS EXITS PER THE EXTERNAL COMMAND: [stop]")
                tl_print(
                    "*****************************************************")
                tl_print("System exits")
                sys.exit()

    def read_external_command(self):
        try:
            html = urllib.request.urlopen(EXTERNAL_COMMAND_URL).read()
            soup = BeautifulSoup(html, features='lxml')
            text = soup.get_text()
            lines = [line.strip() for line in text.splitlines()
                     ]  # strips spaces before and after each word
            command_time = datetime.strptime(lines[0], "%Y%m%d %H:%M:%S")
            ext_command = lines[1]
            if command_time > self.ext_command_last_excution_time_:
                # only if command time is later than init time or last execution time, the command will be executed
                if ext_command in EXTERNAL_COMMAND_LIST:
                    self.ext_command_last_excution_time_ = command_time
                    return [lines[0], ext_command]
            return ['', '']
        except Exception as e:
            # tl_print("Excpetion: Error in read_external_command - ignored: " + str(e))
            return ['', '']
            # Any kinds of errors are ignored

    def status_print(self, to_file=False):
        mb_print = self.master_book.copy()
        mb_print = mb_print.astype(str)
        for i in mb_print.index:
            mb_print.at[i, 'name'] = mb_print.at[i, 'name'][:6]
            mb_print.at[i, 'cprice'] = format(int(mb_print.at[i, 'cprice']),
                                              ',')
            mb_print.at[i, 'nshare'] = format(int(mb_print.at[i, 'nshares']),
                                              ',')
            mb_print.at[i, 'LLB'] = format(
                float(mb_print.at[i, 'LLB']) * 100, '.1f')
            mb_print.at[i, 'LB'] = format(
                float(mb_print.at[i, 'LB']) * 100, '.1f')
            mb_print.at[i, 'UB'] = format(
                float(mb_print.at[i, 'UB']) * 100, '.1f')
            mb_print.at[i, 'invtotal'] = format(
                int(round(float(mb_print.at[i, 'invtotal']) / 1000)), ',')
            mb_print.at[i, 'cvalue'] = format(
                int(round(float(mb_print.at[i, 'cvalue']) / 1000)), ',')
            mb_print.at[i, 'ret'] = format(
                int(round(float(mb_print.at[i, 'ret']) / 1000)), ',')
            mb_print.at[i, 'cash'] = format(
                int(round(float(mb_print.at[i, 'cash']) / 1000)), ',')
            mb_print.at[i, 'retrate'] = format(
                float(mb_print.at[i, 'retrate']) * 100, '.1f')
        mb_print = mb_print.rename(
            columns={
                'cprice': 'cpr',
                'nshares': 'vol',
                'nreinv': 'nr',
                'LLB': 'LL(%)',
                'LB': 'L(%)',
                'UB': 'U(%)',
                'invtotal': 'inv(k)',
                'cvalue': 'cval(k)',
                'retrate': 'rt(%)',
                'ret': 'rt(k)',
                'dec_made': 'dec',
                'active': 'act',
                'cash': 'cash(k)'
            })
        mb_print.drop([0], inplace=True)
        l = [
            'code', 'cpr', 'vol', 'nr', 'LL(%)', 'L(%)', 'U(%)', 'inv(k)',
            'cval(k)', 'rt(%)', 'rt(k)', 'dec', 'act', 'cash(k)', 'name'
        ]

        mb_mobile = mb_print.copy()

        mb_mobile['dec'] = mb_mobile['dec'].map(ABRIDGED_DICT)
        mb_mobile['act'] = mb_mobile['act'].map({'True': 'A', 'False': 'F'})
        mb_mobile['DA'] = mb_mobile['dec'] + mb_mobile['act']

        lm = ['code', 'inv(k)', 'nr', 'rt(%)', 'DA', 'name']

        if to_file == True:
            f = open(STATUS_REPORT_FILE, 'w')
            f.write('master_book (up to last 75 items): \n')
            f.write(
                tabulate(mb_print.loc[-75:, l],
                         headers='keys',
                         showindex=False,
                         tablefmt='simple'))
            f.write('\n')
            f.close()

            m = open(STATUS_REPORT_MOBILE, 'w')
            m.write('master_book (last 75 items): \n')
            m.write(
                tabulate(mb_mobile.loc[-75:, lm],
                         headers='keys',
                         showindex=False,
                         tablefmt='simple'))
            m.write('\n')
            m.close()

        else:
            tl_print(
                'MASTER_BOOK (up to last 75 items): \n',
                tabulate(mb_print.loc[-75:, l],
                         headers='keys',
                         showindex=False,
                         tablefmt='psql'))

        if len(self.trtrade_list) > 0:
            trtrade_list_print = self.trtrade_list.copy()
            for i in trtrade_list_print.index:
                trtrade_list_print.at[i,
                                      'name'] = self.km.get_master_code_name(
                                          trtrade_list_print.at[i, 'code'])

            if to_file == True:
                f = open(STATUS_REPORT_FILE, 'a')
                f.write('trtrade_list (up to last 75 items): \n')
                f.write(
                    tabulate(trtrade_list_print.loc[-75:, :],
                             headers='keys',
                             showindex=False,
                             tablefmt='simple'))
                f.write('\n')
                f.close()

                m = open(STATUS_REPORT_MOBILE, 'a')
                m.write('trtrade_list (last 75 items): \n')
                m.write(
                    tabulate(trtrade_list_print.loc[-75:, :],
                             headers='keys',
                             showindex=False,
                             tablefmt='simple'))
                m.write('\n')
                m.close()
            else:
                tl_print(
                    'trtrade_list (up to last 75 items): \n',
                    tabulate(trtrade_list_print.loc[-75:, :],
                             headers='keys',
                             showindex=False,
                             tablefmt='psql'))
        else:
            if to_file == True:
                f = open(STATUS_REPORT_FILE, 'a')
                f.write('trtrade_list empty \n')
                f.close()
                m = open(STATUS_REPORT_MOBILE, 'a')
                m.write('trtrade_list empty \n')
                m.close()
            else:
                tl_print('trtrade_list empty')

        self.status_summary_report(to_file)

    def status_summary_report(self, to_file=False):
        # Cash at ACCOUNT
        # Cash at TrTrading
        # Total invested amount accross all items
        # Current value total across all items
        # Return rate of TrTrading
        # Realized return total
        # Number of active items
        cash_account = format(
            int(round(int(self.km.get_cash(ACCOUNT_NO)) / 1000)), ',')
        mb_active = self.master_book.loc[self.master_book['active']]
        cash_trtrading = format(
            int(
                round(self.master_book.at[self.master_book.index[-1], 'cash'] /
                      1000)), ',')  # there might not be any active item.
        tr_invested_total = mb_active['invtotal'].sum()
        tr_cvalue_total = mb_active['cvalue'].sum()
        if tr_invested_total > 0:
            tr_return_rate = tr_cvalue_total / tr_invested_total - 1
        else:
            tr_return_rate = 0
        tr_invested_total = format(int(round(tr_invested_total / 1000)), ',')
        tr_cvalue_total = format(int(round(tr_cvalue_total / 1000)), ',')
        tr_return_rate = format(tr_return_rate * 100, '.2f')
        tr_realized_return_total = format(
            int(round(self.master_book['ret'].sum() / 1000)), ',')
        no_active = len(mb_active)
        t = time.strftime("%Y%m%d %H:%M:%S")

        if to_file == True:
            f = open(STATUS_REPORT_FILE, 'a')
            f.write("[TrTrade Summary - " + t + "]" + "\n")
            f.write("- Kiwoom Cash(k): " + cash_account + "\n")
            f.write("- TrTrade Cash(k): " + cash_trtrading + "\n")
            f.write('- Return(%): ' + tr_return_rate + "\n")
            f.write('- #items: ' + str(no_active) + "\n")
            f.write("- Total invested(k): " + tr_invested_total + "\n")
            f.write("- Current Value(k): " + tr_cvalue_total + "\n")
            f.write('- Realized Return Total(k): ' + tr_realized_return_total +
                    "\n")
            f.write('- Exception List: ' + str(TRENDTRADE_EXCEPT_LIST) + "\n")
            f.close()
            m = open(STATUS_REPORT_MOBILE, 'a')
            m.write("[TrTrade Summary - " + t + "]" + "\n")
            m.write("- Kiwoom Cash(k): " + cash_account + "\n")
            m.write("- TrTrade Cash(k): " + cash_trtrading + "\n")
            m.write('- Return(%): ' + tr_return_rate + "\n")
            m.write('- #items: ' + str(no_active) + "\n")
            m.write("- Total invested(k): " + tr_invested_total + "\n")
            m.write("- Current Value(k): " + tr_cvalue_total + "\n")
            m.write('- Realized Return Total(k): ' + tr_realized_return_total +
                    "\n")
            m.write('- Exception List: ' + str(TRENDTRADE_EXCEPT_LIST) + "\n")
            m.close()
        else:
            tl_print("[TrTrade Summary - " + t + ']')
            tl_print("- Kiwoom Cash(k): " + cash_account)
            tl_print("- TrTrade Cash(k): " + cash_trtrading)
            tl_print('- Return(%): ' + tr_return_rate)
            tl_print('- #items: ' + str(no_active))
            tl_print("- Total invested(k): " + tr_invested_total)
            tl_print("- Current Value(k): " + tr_cvalue_total)
            tl_print('- Realized Return Total(k): ' + tr_realized_return_total)
            tl_print('- Exception List: ' + str(TRENDTRADE_EXCEPT_LIST))
Example #6
0
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.tr = 0  #총TR요청횟수

        #텔레그램봇
        my_token = '692301814:AAEfmddhyZPcO0Uzh8r5ZehfooTPOvKOOqc'
        self.mybot = telegram.Bot(token=my_token)
        self.chat_id = 544924927

        self.kiwoom = Kiwoom()  #키움인스턴스 생성
        self.kiwoom.comm_connect()  #API로그인

        self.ts_1_p = 'False'  #거래전략1 초기값

        # Timer1
        self.timer = QTimer(self)
        self.timer.start(1000)  #1초 상태바
        self.timer.timeout.connect(self.timeout)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 25)  #25초 잔고조회
        self.timer2.timeout.connect(self.timeout2)

        # Timer3
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 30)  #30초 매수전략1
        self.timer3.timeout.connect(self.timeout3)

        # Timer4
        self.timer4 = QTimer(self)
        self.timer4.start(1000 * 33)  # 33초 매도전략
        self.timer4.timeout.connect(self.timeout4)

        # Timer5
        self.volume_start = 'false'
        self.timer5 = QTimer(self)
        #self.timer5.start(1000 * 60)  # 60초 9시에 급등주알고리즘 시작하기
        #self.timer5.timeout.connect(self.timeout5)

        # Timer7
        self.timer7 = QTimer(self)
        self.timer7.start(1000 * 1800)  # 30분 중간보고
        self.timer7.timeout.connect(self.timeout7)

        self.list700 = []
        self.list600 = []
        self.buy_list = []

        #버튼, 이벤트발생
        self.lineEdit.textChanged.connect(self.code_changed)  #종목코드 입력시
        self.pushButton.clicked.connect(self.send_order)  #현금주문 버튼 클릭시
        self.pushButton_2.clicked.connect(self.check_balance)  #계좌정보 조회
        self.pushButton_3.clicked.connect(self.trading_strategy_1)  #거래전략1호
        self.pushButton_4.clicked.connect(self.quit_app)  #앱종료
        self.pushButton_4.clicked.connect(
            QCoreApplication.instance().quit)  # 앱종료
        self.pushButton_5.clicked.connect(self.test_button)  # 테스트버튼

        #계좌정보
        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        #프로그램시작알림
        self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                             "ㅣ 프로그램이 시작되었습니다.")
        self.mybot.sendMessage(self.chat_id,
                               text=QTime.currentTime().toString("hh:mm:ss") +
                               "\n프로그램이 시작되었습니다.")
Example #7
0
class Bring_stock_data():
    def __init__(self):
        super().__init__()

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.kiwoom.ohlcv = {
            'date': [],
            'open': [],
            'high': [],
            'low': [],
            'close': [],
            'volume': []
        }
        self.kiwoom.df_10001 = {
            'code': [],
            'name': [],
            'month': [],
            'face_value': [],
            'capital': []
        }
        self.kiwoom.df_10002 = {
            'code': [],
            'name': [],
            '매도거래원명1': [],
            '매도거래원1': [],
            '매도거래량1': [],
            '매수거래원명1': [],
            '매수거래원1': [],
            '매수거래량1': []
        }
        self.kiwoom.df_10003 = {'시간': [], '현재가': [], '누적거래량': []}
        self.kiwoom.df_10004 = {
            '총매도잔량': [],
            '총매수잔량': [],
            '시간외매도잔량': [],
            '시간외매수잔량': []
        }
        self.kiwoom.df_10005 = {
            '날짜': [],
            '시가': [],
            '고가': [],
            '저가': [],
            '종가': []
        }
        self.kiwoom.df_10006 = {
            '날짜': [],
            '시가': [],
            '고가': [],
            '저가': [],
            '종가': []
        }
        self.kiwoom.df_20006 = {'일자': [], '시가': [], '고가': [], '저가': []}

    # 주식 기본정보를 df로 받는다.
    def load_item_basic_info(self):
        stock_code = input("stock_code: ")
        start_date = input("start_date: ")
        stock_code = str(stock_code)
        start_date = str(start_date)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.set_input_value("조회일자", start_date)
        self.kiwoom.comm_rq_data("opt10086_req", "opt10086", 0, "0124")

        while self.kiwoom.remained_data == True:
            time.sleep(TR_REQ_TIME_INTERVAL)
            self.kiwoom.set_input_value("종목코드", stock_code)
            self.kiwoom.set_input_value("조회일자", start_date)
            self.kiwoom.comm_rq_data("opt10086_req", "opt10086", 2, "0124")

        df = pd.DataFrame(self.kiwoom.ohlcv,
                          columns=['open', 'high', 'low', 'close', 'volume'],
                          index=self.kiwoom.ohlcv['date'])
        print(df)
        print("save_to_csv")
        df.to_csv(
            "C:\\workplace\\atm_project\\atm_ver_0.1_jh\\item_basic_info.csv",
            mode='w')

        return df

    def get_tr10001_data(self):
        stock_code = input("stock_code: ")
        stock_code = str(stock_code)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "0286")

        print(self.kiwoom.df_10001)

        df = pd.DataFrame(self.kiwoom.df_10001,
                          columns=['name', 'month', 'face_value', 'capital'],
                          index=self.kiwoom.df_10001['code'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr10001.csv",
                  mode='w')

    def get_tr10002_data(self):
        stock_code = input("stock_code: ")
        stock_code = str(stock_code)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.comm_rq_data("opt10002_req", "opt10002", 0, "0129")

        print(self.kiwoom.df_10002)
        df = pd.DataFrame(self.kiwoom.df_10002,
                          columns=[
                              'name', '매도거래원명1', '매도거래원1', '매도거래량1', '매수거래원명1',
                              '매수거래원1', '매수거래량1'
                          ],
                          index=self.kiwoom.df_10002['code'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr10002.csv",
                  mode='w')

    def get_tr10003_data(self):
        stock_code = input("stock_code: ")
        stock_code = str(stock_code)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.comm_rq_data("opt10003_req", "opt10003", 0, "0120")

        while self.kiwoom.remained_data == True:
            time.sleep(TR_REQ_TIME_INTERVAL)
            self.kiwoom.set_input_value("종목코드", stock_code)
            self.kiwoom.comm_rq_data("opt10003_req", "opt10003", 2, "0120")

        print(self.kiwoom.df_10003)
        df = pd.DataFrame(self.kiwoom.df_10003,
                          columns=['현재가', '누적거래량'],
                          index=self.kiwoom.df_10003['시간'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr10003.csv",
                  mode='w')

    def get_tr10004_data(self):
        stock_code = input("종목코드: ")
        stock_code = str(stock_code)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.comm_rq_data("opt10004_req", "opt10004", 0, "0119")

        df = pd.DataFrame(self.kiwoom.df_10004,
                          columns=['총매도잔량', '총매수잔량', '시간외매도잔량', '시간외매수잔량'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr10004.csv",
                  mode='w')

    def get_tr10005_data(self):
        stock_code = input("종목코드: ")
        stock_code = str(stock_code)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.comm_rq_data("opt10005_req", "opt10005", 0, "0124")

        while self.kiwoom.remained_data == True:
            time.sleep(TR_REQ_TIME_INTERVAL)
            self.kiwoom.set_input_value("종목코드", stock_code)
            self.kiwoom.comm_rq_data("opt10005_req", "opt10005", 2, "0124")

        df = pd.DataFrame(self.kiwoom.df_10005,
                          columns=['시가', '고가', '저가', '종가'],
                          index=self.kiwoom.df_10005['날짜'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr10005.csv",
                  mode='w')

    def get_tr10006_data(self):
        stock_code = input("종목코드: ")
        stock_code = str(stock_code)

        self.kiwoom.set_input_value("종목코드", stock_code)
        self.kiwoom.comm_rq_data("opt10006_req", "opt10006", 0, "0124")

        while self.kiwoom.remained_data == True:
            time.sleep(TR_REQ_TIME_INTERVAL)
            self.kiwoom.set_input_value("종목코드", stock_code)
            self.kiwoom.comm_rq_data("opt10006_req", "opt10006", 2, "0124")

        df = pd.DataFrame(self.kiwoom.df_10006,
                          columns=['시가', '고가', '저가', '종가'],
                          index=self.kiwoom.df_10006['날짜'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr10006.csv",
                  mode='w')

    def get_tr20006_data(self):
        market_code = input("업종코드: ")
        start_date = input("기준일자: ")
        market_code = str(market_code)
        start_date = str(start_date)

        self.kiwoom.set_input_value("업종코드", market_code)
        self.kiwoom.set_input_value("기준일자", start_date)
        self.kiwoom.comm_rq_data("opt20006_req", "opt20006", 0, "0602")

        while self.kiwoom.remained_data == True:
            time.sleep(TR_REQ_TIME_INTERVAL)
            self.kiwoom.set_input_value("업종코드", market_code)
            self.kiwoom.set_input_value("기준일자", start_date)
            self.kiwoom.comm_rq_data("opt20006_req", "opt20006", 2, "0602")

        df = pd.DataFrame(self.kiwoom.df_20006,
                          columns=['시가', '고가', '저가'],
                          index=self.kiwoom.df_20006['일자'])
        print(df)
        print("save_to_csv")
        df.to_csv("C:\\workplace\\atm_project\\atm_ver_0.1_jh\\tr20006.csv",
                  mode='w')

    # df를 csv파일로 저장
    def save_df_to_csv(self, df):
        print("stock_save_to_csv")
        df.to_csv(
            "C:\\workplace\\atm_project\\atm_ver_0.1_jh\\item_basic_info.csv",
            mode='w')
Example #8
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.CommConnect()

        # Timer
        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)
        self.timer2.timeout.connect(self.timeout2)

        # Get Account Number
        accouns_num = int(self.kiwoom.GetLoginInfo("ACCOUNT_CNT"))
        accounts = self.kiwoom.GetLoginInfo("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)

    def timeout2(self):
        if self.checkBox.isChecked() == True:
            self.check_balance()

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.GetConnectState()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"
        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def code_changed(self):
        code = self.lineEdit.text()
        code_name = self.kiwoom.GetMasterCodeName(code)
        self.lineEdit_2.setText(code_name)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.SendOrder("SendOrder_req", "0101", account,
                              order_type_lookup[order_type], code, num, price,
                              hoga_lookup[hoga], "")

    def check_balance(self):
        self.kiwoom.init_opw00018_data()

        # Request opw00018
        self.kiwoom.SetInputValue("계좌번호", "8080996211")
        self.kiwoom.SetInputValue("비밀번호", "0000")
        self.kiwoom.CommRqData("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.prev_next == '2':
            time.sleep(0.2)
            self.kiwoom.SetInputValue("계좌번호", "8080996211")
            self.kiwoom.SetInputValue("비밀번호", "0000")
            self.kiwoom.CommRqData("opw00018_req", "opw00018", 2, "2000")

        # Request opw00001
        self.kiwoom.SetInputValue("계좌번호", "8080996211")
        self.kiwoom.SetInputValue("비밀번호", "0000")
        self.kiwoom.CommRqData("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.data_opw00001)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.data_opw00018['single'][i - 1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.data_opw00018['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.data_opw00018['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
Example #9
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.run()
        self.currentTime = datetime.datetime.now()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        # Timer2 실시간 조회 체크박스 체크하면 10초에 한 번씩 데이터 자동 갱신
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)
        self.timer2.timeout.connect(self.timeout2)

        # 선정 종목 리스트
        self.load_buy_sell_list()

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        #self.pushButton_2.clicked.connect(self.check_balance)
        self.check_balance()
        self.save_final_stock()

    def is_trading_time(self):
        vals = []
        current_time = self.currentTime.time()
        for start, end in TRADING_TIME:
            start_time = datetime.time(hour=start[0], minute=start[1])
            end_time = datetime.time(hour=end[0], minute=end[1])
            if (current_time >= start_time and current_time <= end_time):
                vals.append(True)
            else:
                vals.append(False)
                pass
        if vals.count(True):
            return True
        else:
            return False

    """def stock_name(self):
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()
        account = self.comboBox.currentText()

        for row_data in buy_list:
            split_row_data = row_data.split(';')
            code = split_row_data[1]
"""

    #주문을 들어가기 전에 파일에서 불러와서 종목을 확인, 종목의 전일 종가 확인 - 첫 번째 주문 시
    #두 번째 주문부터는 이미 주문 들어간 파일에서 확인
    # 자동 주문
    def trade_stocks(self):
        #self.check_balance()
        auto_buy = []
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        auto_buy += buy_list
        f.close()

        f = open("sell_list.txt", 'rt')
        sell_list = f.readlines()
        f.close()

        account = self.comboBox.currentText()
        close_rate, current_rate = self.run()
        #print("rate: ", rate[2][0])
        print(current_rate)
        # buy list
        for i in range(len(auto_buy)):
            split_row_data = auto_buy[i].split(';')
            hoga = split_row_data[2]
            code = split_row_data[1]
            num = split_row_data[3]
            price = split_row_data[4]
            bdr = split_row_data[5]
            pr = split_row_data[6]
            lr = split_row_data[7]

            #temp = self.kiwoom.opw00018_output['multi'][0][3]
            """for i in range(len(new)):
                price = bdr * new[i]
                price = int(price)
                temp = price % 10
                new_price = price - temp"""
            #print(self.final_stock[0])
            #price = bdr * self.final_stock[cnt]
            """price = int(price)
            temp = price % 10
            new_price = price - """
            print("bdr:", float(bdr))
            # 전날 종가
            new_price = close_rate[i][0] * float(bdr)
            print("cnt:", i)
            print("rate[cnt]", close_rate[i][0])
            print("new_price:", new_price)
            #temp = new_price % 10
            #new_price = new_price - temp
            hoga = "지정가"

            if split_row_data[-1].rstrip(
            ) == '매수전' and new_price <= current_rate[i][
                    0] and self.is_trading_time() == True:
                self.kiwoom.send_order("send_order_req",
                                       "0101", account, 1, code, 1,
                                       int(new_price), hoga_lookup[hoga], "")
                if self.kiwoom.orderNum:
                    for i, row_data in enumerate(buy_list):
                        buy_list[i] = buy_list[i].replace("매수전", "주문완료")
            elif split_row_data[-1].rstrip() == '매수전' and self.is_trading_time(
            ) == False:
                self.kiwoom.send_order("send_order_req", "0101", account, 1,
                                       code, 1, price, hoga_lookup[hoga], "")
                if self.kiwoom.orderNum:
                    for i, row_data in enumerate(buy_list):
                        buy_list[i] = buy_list[i].replace("매수전", "주문완료")

        # sell list
        for row_data in sell_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[2]
            code = split_row_data[1]
            num = split_row_data[3]
            price = split_row_data[4]

            if split_row_data[-1].rstrip() == '매도전':
                self.kiwoom.send_order("send_order_req", "0101", account, 2,
                                       code, num, price, hoga_lookup[hoga], "")

        #파일 정보 변경
        # buy list
        """for i, row_data in enumerate(buy_list):
            buy_list[i] = buy_list[i].replace("매수전", "주문완료")"""

        # file update
        f = open("buy_list.txt", 'wt')
        for row_data in buy_list:
            f.write(row_data)
        f.close()

        # sell list
        for i, row_data in enumerate(sell_list):
            sell_list[i] = sell_list[i].replace("매도전", "주문완료")

        # file update
        f = open("sell_list.txt", 'wt')
        for row_data in sell_list:
            f.write(row_data)
        f.close()

    def load_buy_sell_list(self):
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt')
        sell_list = f.readlines()
        f.close()

        row_count = len(buy_list) + len(sell_list)
        self.tableWidget_3.setRowCount(row_count)

        # buy list
        # j:행, i:열
        for j in range(len(buy_list)):
            row_data = buy_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(
                split_row_data[1].rstrip())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_3.setItem(j, i, item)

        # sell list
        for j in range(len(sell_list)):
            row_data = sell_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(
                split_row_data[1].rstrip())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_3.setItem(len(buy_list) + j, i, item)

        self.tableWidget_3.resizeRowsToContents()

    def save_final_stock(self):
        item_count = len(self.kiwoom.opw00018_output['multi'])
        if (self.is_trading_time() == False):
            self.final_stock = []
            for i in range(item_count):
                row = self.kiwoom.opw00018_output['multi'][i][3]
                self.final_stock.append(row)
            print(self.final_stock)
        #if(self.is_trading_time() == True):
        #종가 파일로 저장.

    def timeout(self):
        market_start_time = QTime(9, 0, 0)
        current_time = QTime.currentTime()

        if current_time > market_start_time and self.trade_stocks_done is False:
            self.trade_stocks()
            self.trade_stocks_done = True

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    # 체크 박스 체크?
    def timeout2(self):
        #if self.checkBox.isChecked():
        self.check_balance()

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw0001TR (예수금 데이터)
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        #balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        # 나머지 칼럼 (table1)
        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        # 행 높이 조절
        self.tableWidget.resizeRowsToContents()

        # Item list (보유 종목별 평가 잔고)
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)
        self.tableWidget_2.resizeRowsToContents()

    def get_ohlcv(self, code, start):
        #self.get_ohlcv("035720", "20190604")
        self.kiwoom.ohlcv = {'date': [], 'close': []}
        self.kiwoom.final = {'close': []}
        self.kiwoom.current = {'current': []}

        self.kiwoom.set_input_value("종목코드", code)
        self.kiwoom.set_input_value("기준일자", start)
        self.kiwoom.set_input_value("수정주가구분", 1)
        self.kiwoom.comm_rq_data("opt10081_req", "opt10081", 0, "0101")

        #time.sleep(0.2)
        #df = DataFrame(self.kiwoom.ohlcv, columns=['close'],
        #              index=self.kiwoom.ohlcv['date'])
        #return self.kiwoom.ohlcv

    def run(self):
        true_close = []
        true_current = []
        code = []
        today = datetime.datetime.today().strftime("%Y%m%d")
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()

        for row_data in buy_list:
            split_row_data = row_data.split(';')
            code.append(split_row_data[1])
        for i in range(len(code)):
            print("code: ", code[i])
            self.get_ohlcv(code[i], today)
            true_close.append(self.kiwoom.final['close'])
            true_current.append(self.kiwoom.current['current'])
        print(true_close)

        f.close()
        return (true_close, true_current)
Example #10
0
 def __init__(self):
     self.kiwoom = Kiwoom.Kiwoom()
     self.kiwoom.comm_connect()
     self.get_code_list() #StockM이 실행되면 한 번만 수행하면 되기 때문에
Example #11
0
class MyWindow(QMainWindow, form_class):
    # QMainWindow: QWidget 상속하는 클래스(위젯 사용할 수 있도록), form_class: pytrader.ui
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()  # Kiwoom 인스턴스 생성
        self.kiwoom.comm_connect()  # 로그인

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)
        self.timer2.timeout.connect(self.timeout2)

        accouns_num = int(
            self.kiwoom.get_login_info("ACCOUNT_CNT"))  # 보유계좌 갯수 (ex. 2)
        accounts = self.kiwoom.get_login_info(
            "ACCNO")  # 구분자 ';'로 연결된 보유계좌 목록을 반환 (ex. 8165088111;8753740831;)

        accounts_list = accounts.split(';')[0:accouns_num]  # 계좌번호를 리스트로 저장
        self.comboBox.addItems(accounts_list)  # 계좌번호를 comboBox에 넣음

        self.lineEdit.textChanged.connect(self.code_changed)  # 종목코드 입력시
        self.pushButton.clicked.connect(self.send_order)  # [현금주문] 버튼 누를시
        self.pushButton_2.clicked.connect(self.check_balance)  # [조회] 버튼 누를시

    def code_changed(self):
        code = self.lineEdit.text()  # 변경된 종목코드 text 받아서
        name = self.kiwoom.get_master_code_name(code)  # 종목코드에 맞는 종목명을 받아옴
        self.lineEdit_2.setText(name)  # 종목명 보여줌

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()  # 계좌번호
        order_type = self.comboBox_2.currentText()  # 신규매수/신규매도/매수취소/매도취소
        code = self.lineEdit.text()  # 종목코드
        hoga = self.comboBox_3.currentText()  # 지정가/시장가
        num = self.spinBox.value()  # 수량
        price = self.spinBox_2.value()  # 가격

        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")

    def timeout(self):  # 화면 왼쪽 아래에 서버 연결 여부와 현재시간 출력
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):  # 실시간 계좌정보 조회 여부
        if self.checkBox.isChecked():
            self.check_balance()

    def check_balance(self):  # 계좌정보 조회
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
Example #12
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.lineEdit.textChanged.connect(self.code_changed)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.GetConnectState()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
Example #13
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.kiwoom.excelfile_initiator()
        self.kospi_codes = self.kiwoom.get_code_list_by_market(MARKET_KOSPI)
        self.kosdaq_codes = self.kiwoom.get_code_list_by_market(MARKET_KOSDAQ)
        self.candidate_codes = [
            '005930', '252670', '122630', '000660', '207940', '035420',
            '006400', '035720', '005380', '034730', '036570', '017670',
            '105560', '096770', '090430', '097950', '018260', '003550',
            '006800', '078930'
        ]

        # There can be limits in the number of timers
        self.timer = QTimer(self)
        self.timer.start(
            1000 * 10)  # Timer for time update: refresh at every 10*1000ms
        self.timer.timeout.connect(self.timeout)

        # self.timer_balance_check = QTimer(self)
        # self.timer_balance_check.start(1000*10)
        # self.timer_balance_check.timeout.connect(self.check_balance)

        self.timer_autotrade_run = QTimer(self)
        self.timer_autotrade_run.start(1000 * AUTOTRADE_INTERVAL)
        self.timer_autotrade_run.timeout.connect(self.timeout_autotrade_run)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order_ui)
        self.pushButton_2.clicked.connect(self.check_balance)
        self.pushButton_3.clicked.connect(self.timeout_autotrade_run)

        self.check_balance()

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm")
        time_msg = "Time: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "Server Connected"
        else:
            state_msg = "Server Not Connected"
        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout_autotrade_run(self):
        current_time = QTime.currentTime()
        if RUN_AUTOTRADE and not RUN_ANYWAY_OUT_OF_MARKET_OPEN_TIME:
            if datetime.datetime.today().weekday() in range(
                    0, 5
            ) and current_time > MARKET_START_TIME and current_time < MARKET_FINISH_TIME:
                self.autotrade_list_gen()
                self.trade_stocks()
                self.label_8.setText("Autotrade executed")
            else:
                self.label_8.setText("Market not open")
        elif RUN_AUTOTRADE:
            self.label_8.setText("Autotrade / market may not open")
            self.autotrade_list_gen()
            self.trade_stocks()
        else:
            self.label_8.setText("Autotrade disabled")

    def code_changed(self):
        code = self.lineEdit.text()
        if len(code) >= CODE_MIN_LENGTH:
            name = self.kiwoom.get_master_code_name(code)
            if name != "":
                self.kiwoom.set_input_value("종목코드", code)
                self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "1001")
                self.lineEdit_2.setText(name)
                self.spinBox_2.setValue(self.kiwoom.cur_price)
            else:
                self.lineEdit_2.setText("")
                self.spinBox_2.setValue(0)
        else:
            self.lineEdit_2.setText("")
            self.spinBox_2.setValue(0)

    def send_order_ui(self):
        order_type_lookup = {'Buy': 1, 'Sell': 2}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = HOGA_LOOKUP[self.comboBox_3.currentText()]
        num = self.spinBox.value()
        if hoga == "00":
            price = self.spinBox_2.value()
        elif hoga == "03":
            price = 0
        res = self.kiwoom.send_order("send_order_req", "0101", account,
                                     order_type_lookup[order_type], code, num,
                                     price, hoga, "")
        if res[0] == 0 and res[1] != "":
            self.label_8.setText("Order sent")
            ###################################
            if self.kiwoom.order_chejan_finished == True:
                self.label_8.setText("Order completed")
        else:
            self.label_8.setText("Errer in order processing")

    def check_balance(self):
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()

    def load_buy_sell_list(self):
        try:
            buy_list = pd.read_excel(EXCEL_BUY_LIST,
                                     index_col=None,
                                     converters={'Code': str})
        except Exception as e:
            print(e)
            buy_list = pd.DataFrame()

        try:
            sell_list = pd.read_excel(EXCEL_SELL_LIST,
                                      index_col=None,
                                      converters={'Code': str})
        except Exception as e:
            print(e)
            sell_list = pd.DataFrame()

        return [buy_list, sell_list]

###########################################################################
##### EXECUTION
###########################################################################

    def trade_stocks(self):
        [buy_list, sell_list] = self.load_buy_sell_list()

        # account
        account = self.comboBox.currentText()
        buy_order = 1
        sell_order = 2

        # buy_list
        for i in buy_list.index:
            if buy_list["Tr"][i] == 'yet' or buy_list["Tr"][i] == 'failed':
                hoga = HOGA_LOOKUP[buy_list["Order_type"][i]]
                if hoga == "00":
                    price = buy_list["Price"][i]
                elif hoga == "03":
                    price = 0
                res = self.kiwoom.send_order("send_order_req", "0101", account,
                                             buy_order, buy_list["Code"][i],
                                             int(buy_list["Amount"][i]), price,
                                             hoga, "")

                if res[0] == 0 and res[1] != "":
                    self.label_8.setText("Order sent: " + str(res[1]))
                    buy_list.at[i, "Tr"] = 'ordered'
                    ###################################
                    if self.kiwoom.order_chejan_finished == True:
                        buy_list.at[i, "Tr"] = 'done'
                else:
                    self.label_8.setText("Errer in order processing")
                    buy_list.at[i, "Tr"] = 'failed'

        buy_list.to_excel(EXCEL_BUY_LIST, index=False)

        # sell_list
        for i in sell_list.index:
            if sell_list["Tr"][i] == 'yet' or sell_list["Tr"][i] == 'failed':
                hoga = HOGA_LOOKUP[sell_list["Order_type"][i]]
                if hoga == "00":
                    price = sell_list["Price"][i]
                elif hoga == "03":
                    price = 0
                res = self.kiwoom.send_order("send_order_req", "0101", account,
                                             sell_order, sell_list["Code"][i],
                                             int(sell_list["Amount"][i]),
                                             price, hoga, "")
                if res[0] == 0 and res[1] != "":
                    self.label_8.setText("Order sent: " + str(res[1]))
                    sell_list.at[i, "Tr"] = 'ordered'
                    ###################################
                    if self.kiwoom.order_chejan_finished == True:
                        buy_list.at[i, "Tr"] = 'done'
                else:
                    self.label_8.setText("Errer in order processing")
                    sell_list.at[i, "Tr"] = 'failed'

        sell_list.to_excel(EXCEL_SELL_LIST, index=False)


###########################################################################
##### ALGORITHMS
###########################################################################

    def autotrade_list_gen(self):

        [code, price] = self.algo_random_choose_buy(3)
        # sell_list = self.algo_random_choose_sell(3)
        sell_list = self.algo_sell_by_return_range(10, -1)

        self.kiwoom.update_buy_list(code, price)
        self.kiwoom.update_sell_list(sell_list)

    def check_speedy_rising_volume(self, code):
        today = datetime.datetime.today().strftime("%Y%m%d")
        df = self.kiwoom.get_ohlcv(code, today)
        volumes = df['volume']

        if len(volumes) < 21:
            return False

        sum_vol20 = 0
        today_vol = 0

        for i, vol in enumerate(volumes):
            if i == 0:
                today_vol = vol
            elif 1 <= i <= 20:
                sum_vol20 += vol
            else:
                break
        avg_vol20 = sum_vol20 / 20

        if today_vol > avg_vol20 * 3:
            return True

        return False

    def algo_speedy_rising_volume(self):
        buy_list_code = []
        for i, code in enumerate(self.kosdaq_codes):
            if self.check_speedy_rising_volume(code):
                buy_list_code.append(code)
        return buy_list_code

    def algo_random_choose_buy(self, BUY_SELL_SIZE):
        buy_list_code = []
        buy_list_price = []
        for i in range(BUY_SELL_SIZE):
            code = random.choice(self.candidate_codes)
            self.kiwoom.set_input_value("종목코드", code)
            self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "1001")
            name = self.kiwoom.get_master_code_name(code)
            price = self.kiwoom.cur_price
            if price > MIN_STOCK_PRICE:
                buy_list_code.append(code)
                buy_list_price.append(price)
        return [buy_list_code, buy_list_price]

    def algo_random_choose_sell(self, BUY_SELL_SIZE):
        my_stock_list = self.kiwoom.get_my_stock_list()
        if len(my_stock_list) > BUY_SELL_SIZE:
            n = list(range(len(my_stock_list)))
            set_to_sell = random.sample(n, BUY_SELL_SIZE)
            return my_stock_list.iloc[set_to_sell]
        else:
            return my_stock_list

    def algo_sell_by_return_range(
            self, upperlimit,
            lowerlimit):  # upperlimit, lowerlimit in percentage
        my_stocks = self.kiwoom.get_my_stock_list()
        profit_sell_list = my_stocks[my_stocks['earning_rate'] > upperlimit]
        loss_sell_list = my_stocks[my_stocks['earning_rate'] < lowerlimit]
        print('Profit Sell List (up to 50 items): \n',
              tabulate(profit_sell_list[:50], headers='keys', tablefmt='psql'))
        print('Loss Sell List (up to 50 items): \n',
              tabulate(loss_sell_list[:50], headers='keys', tablefmt='psql'))
        return profit_sell_list.append(loss_sell_list)
Example #14
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.timer2 = QTimer(self)
        self.timer2.start(1000 *10)
        self.timer2.timeout.connect(self.timeout2)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account, order_type_lookup[order_type], code, num, price, hoga_lookup[hoga], "")

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i - 1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
Example #15
0
class Pymon:
    def __init__(self):
        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()
        self.get_code_list()
        self.excelfile_initiator()

    def get_code_list(self):
        self.kospi_codes = self.kiwoom.get_code_list_by_market(MARKET_KOSPI)
        self.kosdaq_codes = self.kiwoom.get_code_list_by_market(MARKET_KOSDAQ)

    def get_ohlcv(self, code, start):
        self.kiwoom.set_input_value("종목코드", code)
        self.kiwoom.set_input_value("기준일자", start)
        self.kiwoom.set_input_value("수정주가구분", 1)
        self.kiwoom.comm_rq_data("opt10081_req", "opt10081", 0, "0101")

        df = pd.DataFrame(self.kiwoom.ohlcv,
                          columns=['open', 'high', 'low', 'close', 'volume'],
                          index=self.kiwoom.ohlcv['date'])
        return df

    def update_buy_list(self, buy_list_code):
        buy_list = pd.read_excel(EXCEL_BUY_LIST,
                                 index_col=None,
                                 converters={'Code': str})

        for i, code in enumerate(buy_list_code):
            name = self.kiwoom.get_master_code_name(code)
            today = datetime.datetime.today().strftime("%Y%m%d")
            time_ = datetime.datetime.now().strftime("%H:%M:%S")
            self.kiwoom.set_input_value("종목코드", code)
            self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "1001")

            amount = round(ALLOCATION_SIZE / self.kiwoom.cur_price)
            buy_list = buy_list.append(
                {
                    'Date': today,
                    'Time': time_,
                    'Name': name,
                    'Code': code,
                    'Order_type': 'mkt',
                    'Tr': 'yet',
                    'Price': self.kiwoom.cur_price,
                    'Amount': amount
                },
                ignore_index=True)

        print('Buy List: \n',
              tabulate(buy_list, headers='keys', tablefmt='psql'))

        buy_list.to_excel(EXCEL_BUY_LIST, index=False)

    def get_stock_list(self):
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        stock_list = pd.DataFrame(self.kiwoom.opw00018_rawoutput,
                                  columns=[
                                      'name', 'code', 'quantity',
                                      'purchase_price', 'current_price',
                                      'invested_amount', 'current_total',
                                      'eval_profit_loss_price', 'earning_rate'
                                  ])
        for i in stock_list.index:
            stock_list.at[i, 'code'] = stock_list['code'][i][
                1:]  # taking off "A" in front of returned code
        return stock_list.set_index('code')

    def update_sell_list(self, sell_list_code):
        sell_list = pd.read_excel(EXCEL_SELL_LIST,
                                  index_col=None,
                                  converters={'Code': str})
        stock_list = self.get_stock_list()

        for i, code in enumerate(sell_list_code):
            if code in list(stock_list.index):
                name = self.kiwoom.get_master_code_name(code)
                today = datetime.datetime.today().strftime("%Y%m%d")
                time_ = datetime.datetime.now().strftime("%H:%M:%S")
                self.kiwoom.set_input_value("종목코드", code)
                self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0,
                                         "1001")  # getting current price

                amount = stock_list['quantity'][code]
                sell_list = sell_list.append(
                    {
                        'Date': today,
                        'Time': time_,
                        'Name': name,
                        'Code': code,
                        'Order_type': 'mkt',
                        'Tr': 'yet',
                        'Price': self.kiwoom.cur_price,
                        'Amount': amount
                    },
                    ignore_index=True)

        print('Sell List: \n',
              tabulate(sell_list, headers='keys', tablefmt='psql'))
        sell_list.to_excel(EXCEL_SELL_LIST, index=False)

    def excelfile_initiator(self):
        if not os.path.exists(EXCEL_BUY_LIST):
            # create buy list
            bl = xlsxwriter.Workbook(EXCEL_BUY_LIST)
            blws = bl.add_worksheet()

            blws.write('A1', 'Date')  # Date / Time when the item is added
            blws.write('B1', 'Time')
            blws.write('C1', 'Name')
            blws.write('D1', 'Code')
            blws.write('E1', 'Order_type')  # 시장가 ('mkt') vs 지정가 ('fixed')
            blws.write('F1', 'Tr')  # yet: not, done: done
            blws.write('G1',
                       'Price')  # latest price when the list is populated
            blws.write('H1', 'Amount')
            # blws.write('I1', 'Invested_total') # Before any fee and tax
            # blws.write('J1', 'Date_Trans') # Date / Time when the item is purchased
            # blws.write('K1', 'Time_Trans')
            bl.close()

        if not os.path.exists(EXCEL_SELL_LIST):
            # create sell list
            sl = xlsxwriter.Workbook(EXCEL_SELL_LIST)
            slws = sl.add_worksheet()

            slws.write('A1', 'Date')  # Date / Time when the item is added
            slws.write('B1', 'Time')
            slws.write('C1', 'Name')
            slws.write('D1', 'Code')
            slws.write('E1', 'Order_type')  # 시장가 ('mkt') vs 지정가 ('fixed')
            slws.write('F1', 'Tr')  # yet: not, done: done
            slws.write('G1',
                       'Price')  # latest price when the list is populated
            slws.write('H1', 'Amount')  # Amount to sell
            # slws.write('I1', 'Fee_Tax')
            # slws.write('J1', 'Harvested_total') # After fee and tax
            # slws.write('K1', 'Date_Trans') # Date / Time when the item is purchased
            # slws.write('L1', 'Time_Trans')
            sl.close()

###########################################################################
##### ALGORITHMS
###########################################################################

    def check_speedy_rising_volume(self, code):
        today = datetime.datetime.today().strftime("%Y%m%d")
        df = self.get_ohlcv(code, today)
        volumes = df['volume']

        if len(volumes) < 21:
            return False

        sum_vol20 = 0
        today_vol = 0

        for i, vol in enumerate(volumes):
            if i == 0:
                today_vol = vol
            elif 1 <= i <= 20:
                sum_vol20 += vol
            else:
                break
        avg_vol20 = sum_vol20 / 20

        if today_vol > avg_vol20 * 3:
            return True

        return False

    def algo_speedy_rising_volume(self):
        buy_list_code = []
        for i, code in enumerate(self.kosdaq_codes):
            if self.check_speedy_rising_volume(code):
                buy_list_code.append(code)
        return buy_list_code


###########################################################################
##### EXECUTION
###########################################################################

    def run(self):  # has to return True if the list is updated
        current_time = QTime.currentTime()

        # Timer
        while datetime.datetime.today().weekday() in range(
                0, 5
        ) and current_time > MARKET_START_TIME and current_time < MARKET_FINISH_TIME:
            # Algo
            buy_list_code = []
            buy_list_code.append(random.choice(self.kospi_codes))
            buy_list_code.append(random.choice(self.kospi_codes))
            buy_list_code.append(random.choice(self.kospi_codes))
            buy_list_code.append(random.choice(self.kospi_codes))
            buy_list_code.append(random.choice(self.kospi_codes))

            stock_list_codelist = self.get_stock_list().index.tolist()
            sell_list_code = []
            sell_list_code.append(random.choice(stock_list_codelist))
            sell_list_code.append(random.choice(stock_list_codelist))
            sell_list_code.append(random.choice(stock_list_codelist))
            sell_list_code.append(random.choice(stock_list_codelist))
            sell_list_code.append(random.choice(stock_list_codelist))

            pymon.update_buy_list(buy_list_code)
            pymon.update_sell_list(sell_list_code)

            # Checking
            time.sleep(AUTOTRADE_INTERVAL)
            current_time = QTime.currentTime()
            print(current_time.toString("hh:mm:ss"))
Example #16
0
 def __init__(self):
     super().__init__()
     self.kiwoom = Kiwoom()
     self.kiwoom.comm_connect()
Example #17
0
class MainWindow(QMainWindow, gui):
    def __init__(self):
        super().__init__()
        self.setupUi(self)
        self.kiwoom = Kiwoom()
        self.kiwoom.commConnect()

        # get user account ID/PW
        self.account = []
        with open("account.txt", 'r') as f:
            self.account = f.readlines()

        # get account info
        account_cnt = int(self.kiwoom.getLoginInfo("ACCOUNT_CNT"))
        account_no = self.kiwoom.getLoginInfo("ACCNO")
        account_list = account_no.split(';')[0:account_cnt]

        # timer in status bar
        self.timer_status_bar = QTimer(self)
        self.timer_status_bar.start(1000)
        self.timer_status_bar.timeout.connect(self.timeoutStatusBar)

        # timer in table widgets
        self.timer_table = QTimer(self)
        self.timer_table.start(10000)
        self.timer_table.timeout.connect(self.timeoutBalanceTable)

        # Window forms
        self.qtOrder_comboBox_account.addItems(account_list)
        self.qtOrder_lineEdit_item.textChanged.connect(self.itemCodeChanged)
        self.qtOrder_pushButton_sendOrder.clicked.connect(self.sendOrder)
        self.qtTrade_pushButton_check.clicked.connect(self.checkBalance)

        # execute methods
        # self.conductBuySell()     # 현재 '주문완료' 전 일 경우 shutdown 오류 발생
        self.loadBuySellList()
        self.saveDayData()

        # DB
        df = pd.DataFrame(self.kiwoom.ohlcv, self.kiwoom.ohlcv['date'],
                          ['open', 'high', 'low', 'close'])
        con = sqlite3.connect("stock.db")
        df.to_sql('039490', con, if_exists='replace')

    def timeoutStatusBar(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("ap h시 m분 s초")
        time_msg = "현재시간 : " + text_time

        if self.kiwoom.getConnectState() == 1:
            state_msg = "서버 접속 중"
        else:
            state_msg = "서버 끊김"

        self.statusBar = QStatusBar(self)
        self.setStatusBar(self.statusBar)
        self.statusBar.showMessage(state_msg + " | " + time_msg)

    def timeoutBalanceTable(self):
        if self.qtTrade_checkBox_realtime.isChecked() == True:
            self.checkBalance()
        else:
            pass

    def itemCodeChanged(self):
        """ print item code by hangul """
        code = self.qtOrder_lineEdit_item.text()
        name = self.kiwoom.getMasterCodeName(code)
        self.qtOrder_lineEdit_code.setText(name)

    def sendOrder(self):
        order_type_lookup = {"신규매수": 1, "신규매도": 2, "매수취소": 3, "매도취소": 4}
        bid_lookup = {"지정가": "00", "시장가": "03"}

        account = self.qtOrder_comboBox_account.currentText()
        order_type = self.qtOrder_comboBox_order.currentText()
        code = self.qtOrder_lineEdit_item.text()
        bid = self.qtOrder_comboBox_type.currentText()
        num = self.qtOrder_spinBox_qty.value()
        price = self.qtOrder_spinBox_price.value()

        self.kiwoom.sendOrder("sendOrder_req", "0101", account,
                              order_type_lookup[order_type], code, num, price,
                              bid_lookup[bid], "")

    def checkBalance(self):
        current_account = self.qtOrder_comboBox_account.currentText()
        # request opw00001 : 예수금상세현황요청
        self.kiwoom.setInputValue("계좌번호", current_account)
        self.kiwoom.setInputValue("비밀번호", self.account[1])
        self.kiwoom.commRqData("opw00001_req", "opw00001", 0, "2000")

        # request opw00018 : 계좌평가잔고내역요청
        self.kiwoom.setInputValue("계좌번호", current_account)
        self.kiwoom.setInputValue("비밀번호", self.account[1])
        self.kiwoom.commRqData("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.prev_next == '2':
            time.sleep(0.2)
            self.kiwoom.setInputValue("계좌번호", current_account)
            self.kiwoom.setInputValue("비밀번호", self.account[1])
            self.kiwoom.commRqData("opw00018_req", "opw00018", 2, "2000")

        # print balance at table
        item = QTableWidgetItem(self.kiwoom.opw00001_data)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.qtTrade_tableWidget.setItem(0, 0, item)

        for i in range(len(self.kiwoom.opw00018_data['single'])):
            item = QTableWidgetItem(self.kiwoom.opw00018_data['single'][i])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.qtTrade_tableWidget.setItem(0, i + 1, item)
        self.qtTrade_tableWidget.resizeRowsToContents()

        # print own stock items at table
        item_cnt = len(self.kiwoom.opw00018_data['multi'])
        self.qtTrade_tableWidget2.setRowCount(item_cnt)

        for i in range(item_cnt):
            row = self.kiwoom.opw00018_data['multi'][i]
            for j in range(len(row)):
                item = QTableWidgetItem(row[j])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.qtTrade_tableWidget2.setItem(i, j, item)
        self.kiwoom.opw00018_data['multi'] = []
        self.qtTrade_tableWidget2.resizeRowsToContents()

    def saveDayData(self):
        self.kiwoom.setInputValue("종목코드", "039490")
        self.kiwoom.setInputValue("기준일자", "20170123")
        self.kiwoom.setInputValue("수정주가구분", 1)
        self.kiwoom.commRqData("opt10081_req", "opt10081", 0, "0001")

        while self.kiwoom.prev_next == '2':
            self.kiwoom.setInputValue("종목코드", "039490")
            self.kiwoom.setInputValue("기준일자", "20170123")
            self.kiwoom.setInputValue("수정주가구분", 1)
            self.kiwoom.commRqData("opt10081_req", "opt10081", 2, "0001")

    def loadBuySellList(self):
        # read list from files
        f = open("buy_list.txt", "rt")
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", "rt")
        sell_list = f.readlines()
        f.close()

        # set table row
        row_count = len(buy_list) + len(sell_list)
        self.qtAutoList_tableWidget.setRowCount(row_count)

        # buy list
        for i in range(len(buy_list)):
            data = buy_list[i]
            split_data = data.split(';')
            for j in range(len(split_data)):
                if j == 1:
                    name = self.kiwoom.getMasterCodeName(
                        split_data[j].rstrip())
                    item = QTableWidgetItem(name)
                else:
                    item = QTableWidgetItem(split_data[j].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.qtAutoList_tableWidget.setItem(i, j, item)

        # sell list
        for i in range(len(sell_list)):
            data = sell_list[i]
            split_data = data.split(';')
            for j in range(len(split_data)):
                if j == 1:
                    name = self.kiwoom.getMasterCodeName(
                        split_data[j].rstrip())
                    item = QTableWidgetItem(name)
                else:
                    item = QTableWidgetItem(split_data[j].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.qtAutoList_tableWidget.setItem(len(buy_list) + i, j, item)
        self.qtAutoList_tableWidget.resizeRowsToContents()

    def conductBuySell(self):
        bid_lookup = {'지정가': "00", '시장가': "03"}

        # read list from files
        f = open("buy_list.txt", "rt")
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", "rt")
        sell_list = f.readlines()
        f.close()

        # get current account
        account = self.qtOrder_comboBox_account.currentText()

        # buy
        for data in buy_list:
            split_data = data.split(';')
            code = split_data[1]
            bid = split_data[2]
            num = split_data[3]
            price = split_data[4]
        if split_data[-1].rstrip() == '매수전':
            self.kiwoom.sendOrder('sendOrder_req', '0101', account, 1, code,
                                  num, price, bid_lookup[bid], '')

        # update buy list file
        for i, data in enumerate(buy_list):
            buy_list[i] = buy_list[i].replace('매수전', '주문완료')

        f = open('buy_list.txt', 'wt')
        for data in buy_list:
            f.write(data)
        f.close()

        # sell
        for data in sell_list:
            split_data = data.split(';')
            code = split_data[1]
            bid = split_data[2]
            num = split_data[3]
            price = split_data[4]

        if split_data[-1].rstrip() == '매도전':
            self.kiwoom.sendOrder('sendOrder_req', '0101', account, 2, code,
                                  num, price, bid_lookup[bid], '')

        # update sell list file
        for i, data in enumerate(sell_list):
            sell_list[i] = sell_list[i].replace('매도전', '주문완료')

        f = open('sell_list.txt', 'wt')
        for data in buy_list:
            f.write(data)
        f.close()
Example #18
0
    def __init__(self):
        self.ki = kw.Kiwoom()
        self.dB = db.StockDB()

        self.date = date.today() - timedelta(1)
Example #19
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False
        self.bucket = list()
        self.item_list = list()
        self.code_list = list()

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)
        self.timer2.timeout.connect(self.timeout2)

        accounts_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accounts_num]
        self.comboBox.addItems(accounts_list)
        self.comboBox_2.addItems(accounts_list)

        self.codeLineEdit.textChanged.connect(self.code_changed)
        self.codeLineEdit_2.textChanged.connect(self.code_changed_2)
        self.viewButton.clicked.connect(self.check_balance)
        self.resetButton.clicked.connect(self.reset_bucket)
        self.addButton.clicked.connect(self.add_to_bucket)
        self.showButton.clicked.connect(self.show_bucket)
        self.downButton.clicked.connect(self.download_data)
        self.optButton.clicked.connect(self.optimize_weights)
        self.sendButton.clicked.connect(self.send_initial_order)
        self.spinBox.valueChanged.connect(self.asset_num)

        self.LogDisplay = LogDisplay(self)

    def send_order(self):
        order_type_lookup = {
            'Buying': 1,
            'Selling': 2,
            'Cancel Buying': 3,
            'Cancel Selling': 4
        }
        hoga_lookup = {'Limit': "00", 'Market': "03"}

        account = self.comboBox_2.currentText()
        order_type = self.comboBox_3.currentText()
        code2 = self.codeLineEdit_2.text()
        hoga = self.comboBox_4.currentText()
        num = self.spinBox_2.value()
        price = self.spinBox_3.value()

        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code2, num,
                               price, hoga_lookup[hoga], "")

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)
        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()

    # my portfolio
    def code_changed(self):
        code = self.codeLineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.nameLineEdit.setText(name)

    # manual order
    def code_changed_2(self):
        code2 = self.codeLineEdit_2.text()
        name = self.kiwoom.get_master_code_name(code2)
        self.nameLineEdit_2.setText(name)

    def asset_num(self):
        self.num = self.spinBox.value()

    def reset_bucket(self):
        self.bucket = list()
        self.item_list = list()
        self.code_list = list()

    def add_to_bucket(self):
        code = self.codeLineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.nameLineEdit.setText(name)
        self.bucket.append([code, name])

    def show_bucket(self):
        item_count = len(self.bucket)
        print(self.num)
        if self.num != item_count:
            QMessageBox.about(
                self, "Warning!",
                "Item # is different from the number of assets added to your bucket!"
            )
            return

        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]
        self.kiwoom.set_input_value("계좌번호", account_number)

        # Item list
        self.bucketTable.setRowCount(item_count)

        for j in range(item_count):
            row = self.bucket[j]
            self.code_list.append(row[0])
            self.item_list.append(row[1])
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                self.bucketTable.setItem(j, i, item)
        self.bucketTable.resizeRowsToContents()

    def download_data(self):
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]
        self.kiwoom.set_input_value("계좌번호", account_number)
        for code in self.code_list:
            self.kiwoom.get_ohlcv(code)
        QMessageBox.about(self, "Notification", "Download Completed")

    def optimize_weights(self):
        self.po = PortfolioOptimizer(self.code_list)
        QMessageBox.about(self, "Notification", "Calculation Completed")

    def send_initial_order(self):
        df = self.po.init_buy_list.reset_index()
        print("****** Proceeding my initial order ******")
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]
        self.kiwoom.set_input_value("계좌번호", account_number)
        for i in range(len(df)):
            print(
                "{name}({code}) buy {quantity}".format(name=df.iloc[i][1],
                                                       code=df.iloc[i][0],
                                                       quantity=df.iloc[i][5]))
            self.kiwoom.send_order('order_req', '0101', account_number, 1,
                                   df.iloc[i][0], df.iloc[i][5], 0, '03', '')
        print("succeeded")
        QMessageBox.about(self, "Notification", "Order Completed")

    def display_log(self):
        self.LogDisplay()
Example #20
0
 def __init__(self):
     self.kiwoom = Kiwoom.Kiwoom()
     self.kiwoom.comm_connect()
     self.get_code_list()
Example #21
0
 def __init__(self):
     self.kiwoom = Kiwoom.Kiwoom()
     self.kiwoom.comm_connect()
     self.get_code_list()
     self.my = Mysql()
     self.my.connect(MYSQL)
Example #22
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.tr = 0  #총TR요청횟수

        #텔레그램봇
        my_token = '692301814:AAEfmddhyZPcO0Uzh8r5ZehfooTPOvKOOqc'
        self.mybot = telegram.Bot(token=my_token)
        self.chat_id = 544924927

        self.kiwoom = Kiwoom()  #키움인스턴스 생성
        self.kiwoom.comm_connect()  #API로그인

        self.ts_1_p = 'False'  #거래전략1 초기값

        # Timer1
        self.timer = QTimer(self)
        self.timer.start(1000)  #1초 상태바
        self.timer.timeout.connect(self.timeout)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 25)  #25초 잔고조회
        self.timer2.timeout.connect(self.timeout2)

        # Timer3
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 30)  #30초 매수전략1
        self.timer3.timeout.connect(self.timeout3)

        # Timer4
        self.timer4 = QTimer(self)
        self.timer4.start(1000 * 33)  # 33초 매도전략
        self.timer4.timeout.connect(self.timeout4)

        # Timer5
        self.volume_start = 'false'
        self.timer5 = QTimer(self)
        #self.timer5.start(1000 * 60)  # 60초 9시에 급등주알고리즘 시작하기
        #self.timer5.timeout.connect(self.timeout5)

        # Timer7
        self.timer7 = QTimer(self)
        self.timer7.start(1000 * 1800)  # 30분 중간보고
        self.timer7.timeout.connect(self.timeout7)

        self.list700 = []
        self.list600 = []
        self.buy_list = []

        #버튼, 이벤트발생
        self.lineEdit.textChanged.connect(self.code_changed)  #종목코드 입력시
        self.pushButton.clicked.connect(self.send_order)  #현금주문 버튼 클릭시
        self.pushButton_2.clicked.connect(self.check_balance)  #계좌정보 조회
        self.pushButton_3.clicked.connect(self.trading_strategy_1)  #거래전략1호
        self.pushButton_4.clicked.connect(self.quit_app)  #앱종료
        self.pushButton_4.clicked.connect(
            QCoreApplication.instance().quit)  # 앱종료
        self.pushButton_5.clicked.connect(self.test_button)  # 테스트버튼

        #계좌정보
        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        #프로그램시작알림
        self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                             "ㅣ 프로그램이 시작되었습니다.")
        self.mybot.sendMessage(self.chat_id,
                               text=QTime.currentTime().toString("hh:mm:ss") +
                               "\n프로그램이 시작되었습니다.")

    def test_button(self):
        self.timeout7()

    #종료
    def quit_app(self):
        #계좌정보요청
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        self.tr += 1
        bb = self.kiwoom.opw00018_output['single']
        myaccount = '총매입금액: %s원\n총평가금액: %s원\n총평가손익금액: %s원\n총수익률(%%): %s\n추정예탁자산: %s원' % (
            bb[0], bb[1], bb[2], bb[3], bb[4])

        a = len(self.kiwoom.opw00018_output['multi'])
        if a != 0:
            name = []
            num = []
            buy = []
            price = []
            earn = []
            ret = []
            for i in range(a):
                name.append(self.kiwoom.opw00018_output['multi'][i][0])
                num.append(self.kiwoom.opw00018_output['multi'][i][1])
                buy.append(self.kiwoom.opw00018_output['multi'][i][2])
                price.append(self.kiwoom.opw00018_output['multi'][i][3])
                earn.append(self.kiwoom.opw00018_output['multi'][i][4])
                ret.append(self.kiwoom.opw00018_output['multi'][i][5])
            mystocks = {
                '종목': name,
                '수량': num,
                '매입가': buy,
                '현재가': price,
                '평가손익': earn,
                '수익률(%)': ret
            }
            mystocks = DataFrame(mystocks)
            mystocks = mystocks.set_index(['종목'])

        #last 보고
        self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                             "ㅣ 프로그램이 종료되었습니다.")
        self.mybot.sendMessage(
            self.chat_id,
            text=QTime.currentTime().toString("hh:mm:ss") +
            "\n프로그램이 종료되었습니다.\n총 TR 요청 횟수 : %d회\n -----계좌현황-----\n%s\n -----보유종목-----\n%s"
            % (self.tr, myaccount, mystocks))
        time.sleep(3)

    #상태표시줄(현재시간, 서버연결상태)
    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.GetConnectState()
        if state == 1:
            state_msg = "서버가 연결되었습니다."
        else:
            state_msg = "서버가 연결되지 않았습니다."

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()  #계좌정보 실시간 조회

    def timeout3(self):
        if self.ts_1_p == 'True':  #매수전략1 진행시 30초마다 조회
            self.volume_check()

    def timeout4(self):
        self.sell_stocks()  #매도전략

    def timeout5(self):  #9시 이후에 급등주알고리즘 시작
        market_start_time = QTime(9, 5, 0)
        current_time = QTime.currentTime()

        if current_time > market_start_time and self.volume_start == 'false':
            self.volume_start = 'true'
            self.trading_strategy_1()

    def timeout7(self):  #중간보고
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        self.tr += 1

        bb = self.kiwoom.opw00018_output['single']
        myaccount = '총매입금액: %s원\n총평가금액: %s원\n총평가손익금액: %s원\n총수익률(%%): %s\n추정예탁자산: %s원' % (
            bb[0], bb[1], bb[2], bb[3], bb[4])
        print(myaccount)
        a = len(self.kiwoom.opw00018_output['multi'])
        if a != 0:
            name = []
            num = []
            buy = []
            price = []
            earn = []
            ret = []
            for i in range(a):
                name.append(self.kiwoom.opw00018_output['multi'][i][0])
                num.append(self.kiwoom.opw00018_output['multi'][i][1])
                buy.append(self.kiwoom.opw00018_output['multi'][i][2])
                price.append(self.kiwoom.opw00018_output['multi'][i][3])
                earn.append(self.kiwoom.opw00018_output['multi'][i][4])
                ret.append(self.kiwoom.opw00018_output['multi'][i][5])
            mystocks = {
                '종목': name,
                '수량': num,
                '매입가': buy,
                '현재가': price,
                '평가손익': earn,
                '수익률(%)': ret
            }
            mystocks = DataFrame(mystocks)
            mystocks = mystocks.set_index(['종목'])
        print(mystocks)
        # 중간보고
        self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                             "ㅣ 중간보고 완료.")
        print('hi')
        self.mybot.sendMessage(
            self.chat_id,
            text=QTime.currentTime().toString("hh:mm:ss") +
            "\n--------중간보고--------\n총 TR 요청 횟수 : %d회\n --------계좌현황--------\n%s\n --------보유종목--------\n%s"
            % (self.tr, myaccount, mystocks))

    #종목명 나타내기
    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    #현금주문(수동주문)
    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")
        self.tr += 1

    #계좌정보
    def check_balance(self):

        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        self.tr += 1
        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")
        self.tr += 1

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
        print('잔고조회완료')

    #거래량급증 거래전략1
    def trading_strategy_1(self):

        if self.ts_1_p == 'False':
            print('ts_1_p = true, 매수전략1 실행중입니다.')
            self.ts_1_p = 'True'
            self.label_7.setText("진행중...")
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                                 "ㅣ 매수전략1 시작되었습니다.")
            self.mybot.sendMessage(
                self.chat_id,
                text=QTime.currentTime().toString("hh:mm:ss") +
                "ㅣ 매수전략1 시작되었습니다.")
            self.volume_check()

        elif self.ts_1_p == 'True':
            print('ts_1_p = False, 매수전략1 중지되었습니다.')
            self.label_7.setText("")
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                                 "ㅣ 매수전략1 중지되었습니다.")
            self.mybot.sendMessage(
                self.chat_id,
                text=QTime.currentTime().toString("hh:mm:ss") +
                "ㅣ 매수전략1 중지되었습니다.")
            self.ts_1_p = 'False'

    #매수,매도주문
    def order_stocks(self, bs, code, num, price, set_price):
        '''
        :param bs: 매수=1 매도=2
        :param code: 종목코드
        :param num: 수량
        :param price: 가격 (시장가이면 0)
        :param set_price: 지정가=00 시장가=03
        :return:
        '''
        account = self.comboBox.currentText()

        # order
        self.kiwoom.send_order("send_order_req", "0101", account, bs, code,
                               num, price, set_price, "")
        self.tr += 1

    #거래량급증 조회
    def volume_check(self):
        market_list = ['kospi', 'kosdaq']
        print('조회수급등조회시작')
        for market in market_list:
            if market == 'kospi':
                url = 'https://finance.naver.com/sise/sise_quant_high.nhn'
            elif market == 'kosdaq':
                url = 'https://finance.naver.com/sise/sise_quant_high.nhn?sosok=1'
            html = requests.get(url).text

            df = pd.DataFrame()
            df = df.append(pd.read_html(html, header=0)[1])
            df = df.dropna()
            df = df.rename(
                columns={
                    'N': 'num',
                    '증가율': 'rate',
                    '종목명': 'name',
                    '현재가': 'price',
                    '전일비': 'diff',
                    '등락률': 'updown',
                    '매수호가': 'buy_hoga',
                    '매도호가': 'sell_hoga',
                    '거래량': 'volume',
                    '전일거래량': 'yes_volume',
                    'PER': 'PER'
                })
            df = df.set_index(['num'])  #크롤링완료

            #700이상
            df700 = df[[a > 700 for a in df.rate]]
            a700 = list(df700['name'])
            if len(df700) != 0:
                for i in range(len(df700)):
                    a = html.find(a700[i])
                    code = html[a - 22:a - 16]
                    self.list700.append(code)

            #교집합 구하기
            aa = set(self.list700)
            bb = set(self.list600)
            buy_set = aa & bb
            buy_set = list(buy_set)
            if len(buy_set) != 0:
                for i in range(len(buy_set)):
                    self.buy_list.append(buy_set[i])

            #600~700
            self.list600 = []
            df600 = df[[a > 400 and a < 700 for a in df.rate]]
            a600 = list(df600['name'])
            if len(df600) != 0:
                for i in range(len(df600)):
                    a = html.find(a600[i])
                    code = html[a - 22:a - 16]
                    self.list600.append(code)

        print('매수리스트: %s' % self.buy_list)

        #order
        if len(self.buy_list) == 0:
            pass
        else:
            account_number = self.comboBox.currentText()
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")
            buy_q = int(self.kiwoom.d2_deposit[:-3].replace(',', ''))
            buy_q = (buy_q // len(self.buy_list)) // 5  #예수금/선정종목갯수/5
            self.tr += 1

            for code in self.buy_list:
                time.sleep(0.5)
                self.kiwoom.set_input_value("종목코드", code)
                self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "0101")
                self.tr += 1

                self.order_stocks(1, code, buy_q, 0, '03')
                self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") +
                                     'ㅣ 매수주문\n종목: %s\n수량: %d\n가격: 시장가' %
                                     (self.kiwoom.stock_name, buy_q))
                self.mybot.sendMessage(
                    self.chat_id,
                    text=QTime.currentTime().toString('hh:mm:ss') +
                    'ㅣ매수주문\n 종목: %s\n수량: %d\n가격: 시장가' %
                    (self.kiwoom.stock_name, buy_q))
        self.buy_list = []
        self.list700 = []
        print("거래량급증조회완료")

    #목표수익률 도달시 팔기
    def sell_stocks(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        self.tr += 1

        list_1 = list(self.kiwoom.opw00018_output['multi'])
        a = len(list_1)
        if a != 0:
            print('보유종목현황: %s' % list_1)
            for i in range(a):
                if float(list_1[i][5]) > 5:
                    code = list_1[i][6]
                    num = int(list_1[i][1].replace('.00', '').replace(',', ''))
                    self.kiwoom.set_input_value("종목코드", code)
                    self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0,
                                             "0101")
                    self.tr += 1
                    self.order_stocks(2, code, num, 0, '03')
                    print('매도종목: %s' % code)
                    self.mybot.sendMessage(
                        self.chat_id,
                        text=QTime.currentTime().toString("hh:mm:ss") +
                        'ㅣ 매도주문\n 종목: %s\n수량: %d\n가격: 시장가' %
                        (self.kiwoom.stock_name, num))
                    self.textEdit.append(
                        QTime.currentTime().toString("hh:mm:ss") +
                        'ㅣ 매도주문\n 종목: %s\n수량: %d\n가격: 시장가' %
                        (self.kiwoom.stock_name, num))
                elif float(list_1[i][5]) < -3:
                    code = list_1[i][6]
                    num = int(list_1[i][1].replace('.00', '').replace(',', ''))
                    self.kiwoom.set_input_value("종목코드", code)
                    self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0,
                                             "0101")
                    self.tr += 1
                    print('매도종목: %s' % code)
                    self.order_stocks(2, code, num, 0, '03')
                    self.mybot.sendMessage(
                        self.chat_id,
                        text=QTime.currentTime().toString("hh:mm:ss") +
                        'ㅣ 매도주문\n 종목: %s\n수량: %d\n가격: 시장가' %
                        (self.kiwoom.stock_name, num))
                    self.textEdit.append(
                        QTime.currentTime().toString("hh:mm:ss") +
                        'ㅣ 매도주문\n 종목: %s\n수량: %d\n가격: 시장가' %
                        (self.kiwoom.stock_name, num))
Example #23
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False  # 자동 trading False이면 작동

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()
        # 전략
        self.stratagy = SysStratagy()

        # Timer1
        self.timer = QTimer(self)
        self.timer.start(1000 * 5)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)

        # Timer3
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 10)

        # Timer4 손절처리를 위한 Timer 설정
        self.timer4 = QTimer(self)
        self.timer4.start(1000 * 60)

        # Naver에서 현재가 가져오기
        self.timer_naver = QTimer(self)
        self.timer_naver.start(1000 * 4)

        # Naver에서 현재가 가져오기
        self.timer_rate = QTimer(self)
        self.timer_rate.start(1000 * 3)

        # 계좌정보 넣어줌
        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        # 보유 종목정보
        self.boyou_stock_list = []
        self.check_balance()
        self.init_boyou_stock_list = self.kiwoom.opw00018_output['multi']
        self.boyou_stock_list = self.init_boyou_stock_list
        # self.boyou_stock_list.append(['삼성전자', '100', '40000', '42000', '200000', '5', '005930'])
        # 아침에 보유주식 매도기능 주석처리함.. 보유주식 정보에서 처리하면 되므로 2019.05.19
        # 보유 주식 매도 주문 아침9시전에 구동시에 보유주식에 대한 매도주문처리
        # self.init_boyou_mado()

        # 매도/매수 리스트 조회
        self.load_buy_sell_list()

        # 보유주식정보 json으로 저장
        self.boyoustock = BoyouStock()
        self.boyou_stock_save_json()

        # 이벤트 정보 연결
        self.timer.timeout.connect(self.timeout)
        self.timer2.timeout.connect(self.timeout2)
        self.timer3.timeout.connect(self.timeout3)
        self.timer4.timeout.connect(
            self.timeout4)  # stop loss 처리 # 보유주식정보 가져오는 것으로 수정함.2019.05.19
        self.timer_naver.timeout.connect(self.timeout_naver)
        self.timer_rate.timeout.connect(self.timeout_rate)
        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(
            self.check_balance_Widget
        )  # pushButton_2 라는 객체가 클릭될 때 check_balance라는 메서드가 호출

        # 손절,익절률 설정 값 읽어오기
        config = self.boyoustock.readConfig()
        if len(config) > 0:
            self.stop_profit_rate = (config["stop_profit_rate"] / 100) + 1
            self.stop_loss_rate = 1 - (config["stop_loss_rate"] / 100)
            self.spinBox_6.setValue(config["stop_profit_rate"])
            self.spinBox_7.setValue(config["stop_loss_rate"])
        else:
            self.stop_profit_rate = (self.spinBox_6.value() / 100) + 1
            self.stop_loss_rate = 1 - (self.spinBox_7.value() / 100)
        print("초기 설정 익절률: " + str(self.stop_profit_rate))
        print("초기 설정 손절률: " + str(self.stop_loss_rate))

    def init_boyou_mado(self):
        market_start_time = QTime(9, 0, 0)
        current_time = QTime.currentTime()

        # self.init_maedo_proc()

        if current_time < market_start_time:
            # 보유종목 매도 처리..
            self.init_maedo_proc()
        else:
            print("보유주식에 대한 매도주문은 9시전에만 가능함.")

    def timeout(self):
        # market_start_time = QTime(8, 0, 0)
        # market_end_time = QTime(19, 0, 0)
        current_time = QTime.currentTime()

        if self.stratagy.isTimeAvalable(self.kiwoom.maesu_start_time,
                                        self.kiwoom.maesu_end_time
                                        ) and self.trade_stocks_done is False:
            self.trade_stocks()
            # self.trade_stocks_done = True
        else:
            print("지금은 거래 가능한 시간이 아닙니다.")
            self.kiwoom.comm_terminate()
            sys.exit(1)

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance_Widget()

    def timeout3(self):
        if self.checkBox_2.isChecked():
            self.load_buy_sell_list()

    def timeout4(self):
        self.boyoustock.readBoyouStockInfo()
        # if self.checkBox_3.isChecked():  # 일단주석처리.
        #     self.stock_stop_loss()

    def timeout_naver(self):
        self.cur_stock_price_naver()

    def timeout_rate(self):
        config = {}
        profit = (self.spinBox_6.value() / 100) + 1
        loss = 1 - (self.spinBox_7.value() / 100)
        if self.stop_profit_rate != profit:
            self.stop_profit_rate = profit
            self.spinBox_6.setValue(self.spinBox_6.value())
            config["stop_profit_rate"] = self.spinBox_6.value()
            config["stop_loss_rate"] = self.spinBox_7.value()
            self.boyoustock.updateConfig(config)
            print("익절률이 변경되었습니다. TO " + str(profit))
        if self.stop_loss_rate != loss:
            self.stop_loss_rate = loss
            self.spinBox_7.setValue(self.spinBox_7.value())
            config["stop_profit_rate"] = self.spinBox_6.value()
            config["stop_loss_rate"] = self.spinBox_7.value()
            self.boyoustock.updateConfig(config)
            print("손절률이 변경되었습니다. TO " + str(loss))

    def boyou_stock_save_json(self):
        if len(self.init_boyou_stock_list) > 0:
            init_stock_list = []
            self.boyoustock.updateBoyouStockInfo(init_stock_list)
            for key in range(len(self.init_boyou_stock_list)):
                row = self.boyou_stock_list[key]
                boyou_cnt = int(row[1].replace(',', ''))
                maeip_price = int(row[2].replace(',', ''))
                # cur_price = int(row[3].replace(',', ''))
                stock_code = row[6]
                stock_name = row[0]
                mado_price = self.stratagy.get_maedo_price(
                    maeip_price, self.stop_loss_rate)  # 5% 손절가처리
                sell_price = self.stratagy.get_maedo_price(
                    maeip_price, self.stop_profit_rate)  # 목표가 처리
                self.boyoustock.stock_buy([
                    stock_code, stock_name, maeip_price, boyou_cnt, sell_price,
                    mado_price
                ])
        else:
            init_stock_list = []
            self.boyoustock.updateBoyouStockInfo(init_stock_list)

    def cur_stock_price_naver(self):
        # self.chg_boyou_stock_list = self.kiwoom.opw00018_output['multi']
        # # 초기에 보유주식과 매수/매도가 발생시 보유 주식이 다를 수 있으므로
        # # 이렇게 처리함..
        # logger.debug("== cur_stock_price_naver ==")
        # logger.debug((self.init_boyou_stock_list, self.chg_boyou_stock_list))
        # if util.list_diff(self.init_boyou_stock_list, self.chg_boyou_stock_list):
        #     self.boyou_stock_list = self.chg_boyou_stock_list
        self.boyou_stock_list = self.boyoustock.readBoyouStockInfo()
        for key in range(len(self.boyou_stock_list)):
            bstock = self.boyou_stock_list[key]
            stock_cd = bstock[0]  # 주식코드
            stock_nm = bstock[1]  # 주식명
            maeip_price = bstock[2]  # 매입단가
            maeip_qtr = bstock[3]  # 매입수
            stop_price = self.stratagy.get_maedo_price(
                maeip_price, self.stop_loss_rate)  # -5% 손절가
            dest_price = self.stratagy.get_maedo_price(
                maeip_price, self.stop_profit_rate)  # 목표가 도달시
            cur_price = util.get_naver_cur_stock_price(
                stock_cd)  # 네이버에서 가져온 현재가
            logger.debug(util.cur_date_time() + '보유주식명:' + stock_nm +
                         ',주식코드:' + stock_cd + ',현재가:' + str(cur_price) +
                         ',예상 손절가:' + str(stop_price))
            if cur_price <= stop_price:
                logger.debug(util.cur_date_time() + '손절 프로세스 진행 ===> 보유주식명:' +
                             stock_nm + ',주식코드:' + stock_cd + ',현재가:' +
                             str(cur_price) + ',예상 손절가:' + str(stop_price))
                # self.stock_stop_loss(stock_cd, maeip_qtr, stop_price)
                self.add_init_stock_sell_info(stock_cd, dest_price, maeip_qtr,
                                              'S')
            elif cur_price >= dest_price:
                logger.debug(util.cur_date_time() +
                             '이익 매도 프로세스 진행 ===> 보유주식명:' + stock_nm +
                             ',주식코드:' + stock_cd + ',현재가:' + str(cur_price) +
                             ',예상 손절가:' + str(stop_price))
                self.add_init_stock_sell_info(stock_cd, dest_price, maeip_qtr,
                                              'I')

    # 이익을 위한 매도주문(즉시 매도처리 이므로)을 취소하고 손실을 중지하기 위한 주문처리를 함.
    def stock_stop_loss(self, t_stock_code, num, price):
        is_existed_stock = False
        self.check_balance()
        item_count = len(self.kiwoom.opw00018_output['multi'])
        logger.debug("itemCount ==> " + str(item_count))
        if item_count == 0:
            logger.debug("보유종목이 없습니다.")

        # 한 종목에 대한 종목명, 보유량, 매입가, 현재가, 평가손익, 수익률(%)은 출력
        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            stock_code = row[6]
            if t_stock_code == stock_code:
                is_existed_stock = True

        if is_existed_stock:
            order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
            hoga_lookup = {'지정가': "00", '시장가': "03"}

            account = self.comboBox.currentText()

            self.kiwoom.send_order("send_order_req", "0101", account,
                                   order_type_lookup['신규매도'], t_stock_code,
                                   num, price, hoga_lookup['시장가'], "")
        else:
            print("이미 매도 되었거나 매수되지 않은 주식입니다.")

        # logger.debug("=== stock_stop_loss ===")
        # logger.debug("손실에 대한 loss 처리 설정했습니다.")
        # self.check_balance()
        # # Item list
        # item_count = len(self.kiwoom.opw00018_output['multi'])
        # logger.debug("itemCount ==> " + str(item_count))
        # if item_count == 0:
        #     logger.debug("보유종목이 없습니다.")
        #
        # # 한 종목에 대한 종목명, 보유량, 매입가, 현재가, 평가손익, 수익률(%)은 출력
        # for j in range(item_count):
        #     row = self.kiwoom.opw00018_output['multi'][j]
        #     boyou_cnt = int(row[1].replace(',', ''))
        #     maeip_price = int(row[2].replace(',', ''))
        #     cur_price = int(row[3].replace(',', ''))
        #     stock_code = row[6]
        #     logger.debug(util.cur_date_time() + "현재보유주식코드=>" + stock_code + ",손절주식코드=>" + t_stock_code)
        #     if stock_code == t_stock_code:
        #         # 보유종목의 이익매도 주문이 있는 경우 이익매도주문 취소후 익절처리
        #         self.check_michegyoel_joomoon(stock_code)
        #         row2 = self.kiwoom.opw00007_output[j]
        #         if len(row2) > 0:
        #             if row2[5] != '':
        #                 orgJoomoonNo = int(row2[5])  # 원주문번호 정보를 가져온다.
        #                 self._file_line_delete(self.kiwoom.sell_loc, stock_code)  # stor파일에 해당 종목을 삭제한다.
        #             else:
        #                 orgJoomoonNo = ''
        #         else:
        #             orgJoomoonNo = ""
        # logger.debug(util.cur_date_time() + ":보유주식수/ 매입가/주식코드/원주문번호: %s %s %s %s" % (boyou_cnt, maeip_price, stock_code, orgJoomoonNo))

        # if orgJoomoonNo != "":
        #     self.kiwoom.add_stock_sell_info_loss(stock_code, 0, boyou_cnt, orgJoomoonNo)
        # else:
        #     self.add_init_stock_sell_info(stock_code, 0, boyou_cnt, 'S')

        # print("종목코드 :", stock_code, " 원주문번호 : ", orgJoomoonNo)
        # logger.debug(util.cur_date_time() + ":보유주식수/ 매입가/주식코드/원주문번호: %s %s %s %s" % (
        # boyou_cnt, maeip_price, stock_code, orgJoomoonNo))
        # mado_price = self.stratagy.get_maedo_price(maeip_price, 0.95)  # 4% 익절가처리
        # 해당주식의 (이익을 얻기 위한)매도 주문 취소 처리
        # 아침에 자동 매도주문 처리가 됐을것이고 그것에 대해 취소처리를 하는 것..
        # if not self._item_stock_exist(stock_code):
        # logger.debug(util.cur_date_time() + " : 현재가 / 손절가: %s %s " % (cur_price, mado_price))
        # 일단 주석처리 2019.05.02
        # if cur_price < mado_price: # 익절가보다 작으면 매도처리
        #     if orgJoomoonNo != "":
        #         self.kiwoom.add_stock_sell_info_loss(stock_code, mado_price, boyou_cnt, orgJoomoonNo)
        #     else:
        #         self.add_init_stock_sell_info(stock_code, mado_price, boyou_cnt, 'S')

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def get_boyou_cnt(self):
        self.check_balance()
        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        if item_count == 0:
            print("보유종목이 없습니다.")
        return item_count

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]  # 첫번째 계좌번호 호출

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

    def check_michegyoel_joomoon(self, code):
        self.kiwoom.reset_opw00007_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]  # 첫번째 계좌번호 호출
        joomoondate = util.cur_date('%y%m%d')
        self.kiwoom.set_input_value("주문일자", joomoondate)
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.set_input_value("비밀번호", "3051")
        self.kiwoom.set_input_value("비밀번호매체구분", "00")
        self.kiwoom.set_input_value("조회구분", "3")
        self.kiwoom.set_input_value("주식채권구분", "1")
        self.kiwoom.set_input_value("매도매수구분", "1")
        self.kiwoom.set_input_value("종목코드", code)
        self.kiwoom.set_input_value("시작주문번호", "")
        self.kiwoom.comm_rq_data("opw00007_req", "opw00007", 0, "2000")

    def check_balance_Widget(self):
        self.check_balance()
        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        # 총매입, 총평가, 총손익, 총수익률(%), 추정자산을 QTableWidget의 칼럼에 추가하는 코드.
        # 데이터는 self.kiwoom.opw00018_output['single']을 통해 얻어올 수 있음.
        for i in range(1, 6):
            print('Debug', self.kiwoom.opw00018_output['single'][i - 1])
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        # resizeRowsToContents 메서드를 호출해서 아이템의 크기에 맞춰 행의 높이를 조절
        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        # 한 종목에 대한 종목명, 보유량, 매입가, 현재가, 평가손익, 수익률(%)은 출력
        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        # resizeRowsToContents 메서드를 호출해서 아이템의 크기에 맞춰 행의 높이를 조절
        self.tableWidget.resizeRowsToContents()

    def load_buy_sell_list(self):
        f = open(self.kiwoom.buy_loc, 'rt', encoding='UTF-8')
        buy_list = f.readlines()
        f.close()

        f = open(self.kiwoom.sell_loc, 'rt', encoding='UTF-8')
        sell_list = f.readlines()
        f.close()

        row_count = len(buy_list) + len(sell_list)
        self.tableWidget_3.setRowCount(row_count)

        # buy list
        for j in range(len(buy_list)):
            row_data = buy_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(
                split_row_data[1].rsplit())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_3.setItem(j, i, item)

        # sell list
        for j in range(len(sell_list)):
            row_data = sell_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(
                split_row_data[1].rstrip())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_3.setItem(len(buy_list) + j, i, item)

        self.tableWidget_3.resizeRowsToContents()

    # 프로그램 시작시, 보유종목에 대한 매도처리
    def init_maedo_proc(self):
        self.check_balance()
        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        if item_count == 0:
            print("보유종목이 없습니다. [", item_count, "]")
            pass
        # 한 종목에 대한 종목명, 보유량, 매입가, 현재가, 평가손익, 수익률(%)은 출력
        stratagy = SysStratagy()
        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            boyou_cnt = int(row[1].replace(',', ''))
            maeip_price = int(row[2].replace(',', ''))
            stock_code = row[6]
            mado_price = stratagy.get_maedo_price(maeip_price,
                                                  self.stop_profit_rate)
            self.add_init_stock_sell_info(stock_code, mado_price, boyou_cnt,
                                          'I')

    # 매도 Stor에 매도 종목 추가
    def add_init_stock_sell_info(self, code, sell_price, sell_qty, status):
        dm = ';'
        b_gubun = "매도"
        b_status = "매도전"
        b_price = sell_price
        if status == 'I':
            b_method = "지정가"
        else:
            b_method = "시장가"
        b_qty = sell_qty
        included = False
        code_info = self.kiwoom.get_master_code_name(code)
        mste_info = self.kiwoom.get_master_construction(code)
        stock_state = self.kiwoom.get_master_stock_state(code)
        print(code_info, mste_info, stock_state)

        f = open(self.kiwoom.sell_loc, 'rt', encoding='UTF-8')
        sell_list = f.readlines()
        f.close()

        if self.stratagy.isTimeAvalable(self.kiwoom.maesu_start_time,
                                        self.kiwoom.maesu_end_time):
            if len(sell_list) > 0:
                write_mode = 'a'  # 추가
            else:
                write_mode = 'wt'
            for stock in sell_list:
                if code in stock:
                    included = True
                else:
                    included = False
            if not included:
                f = open(self.kiwoom.sell_loc, write_mode, encoding='UTF-8')
                stock_info = b_gubun + dm + code + dm + b_method + dm + str(
                    b_qty) + dm + str(b_price) + dm + b_status + dm
                f.write(stock_info + '\n')
                f.close()
        else:
            f = open(self.kiwoom.sell_loc, 'wt', encoding='UTF-8')
            stock_info = b_gubun + dm + code + dm + b_method + dm + str(
                b_qty) + dm + str(b_price) + dm + b_status + dm
            f.write(stock_info + '\n')
            f.close()

    # buy_list는 애초에 모니터링시 기본정보 목록에서 추출
    # 매매전략에 해당하는 종목을 buy_list_txt에 저장
    def trade_buy_stratagic(self, code):
        stockInfo = {}
        stockInfo = self.get_current_info(code)
        if stockInfo is not None and len(stockInfo) > 0:
            print('종목정보 : ', stockInfo)
            name = self.kiwoom.get_master_code_name(code)
            cur_price = stockInfo.get('현재가')
            open_price = stockInfo.get('시가')
            print('현재가 :', cur_price, ' 시가:', open_price)
            if open_price == '' or cur_price == '':
                return False
            else:
                if cur_price[0] == '-' or cur_price[0] == '+':
                    cur_price = cur_price[1:]
                if open_price[0] == '-' or open_price[0] == '+':
                    open_price = open_price[1:]
                result = self.stratagy.isBuyStockAvailable(
                    code, name, cur_price, open_price, s_year_date)
        else:
            self.kiwoom.set_input_value("종목코드", code)
            self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "2000")
            name = self.kiwoom.get_master_code_name(code)
            # cur_price = self.kiwoom.jangoInfo[code]['현재가']
            # if cur_price[0] == '-' or cur_price[0] == '+':
            #     cur_price = cur_price[1:]
            # open_price = self.kiwoom.jangoInfo[code]['시가']
            # if cur_price[0] == '-' or cur_price[0] == '+':
            #     open_price = open_price[1:]
            # print(name, ",현재가 : ", self.kiwoom.cur_price)
            result = self.stratagy.isBuyStockAvailable(code, name,
                                                       self.kiwoom.cur_price,
                                                       self.kiwoom.open_price,
                                                       s_year_date)

        # 주식 정상상태 로직 추가 2019.04.20 start
        mste_info = self.kiwoom.get_master_construction(code)
        if mste_info == '정상' and result is True:
            result = True
        else:
            result = False
        # End

        return result
        # return True

    def _file_update(self, fileName, code, pre_status, chg_status):
        stock_list = []
        f = open(fileName, 'rt', encoding='UTF-8')
        stock_list = f.readlines()
        f.close()

        for i, row_data in enumerate(stock_list):
            if code in stock_list[i]:
                stock_list[i] = stock_list[i].replace(pre_status, chg_status)

        # file update
        f = open(fileName, 'wt', encoding='UTF-8')
        for row_data in stock_list:
            f.write(row_data)
        f.close()

    def _file_line_delete(self, fileName, code):
        stock_list = []
        f = open(fileName, 'rt', encoding='UTF-8')
        stock_list = f.readlines()
        f.close()

        for i, row_data in enumerate(stock_list):
            if code in stock_list[i]:
                stock_list[i + 1].remove()

        # file update
        f = open(fileName, 'wt', encoding='UTF-8')
        for row_data in stock_list:
            f.write(row_data)
        f.close()

    def _item_stock_exist(self, fileName, code):
        stock_list = []
        f = open(fileName, 'rt', encoding='UTF-8')
        stock_list = f.readlines()
        f.close()
        b_exist = False
        for i, row_data in enumerate(stock_list):
            if code in stock_list[i]:
                b_exist = True

        return b_exist

    def get_current_info(self, code):
        return self.kiwoom.jongmokInfo.get(code)

    def get_current_info_tr(self, code):
        self.kiwoom.set_input_value("종목코드", code)
        self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "2000")

    def trade_stocks(self):
        if self.stratagy.isTimeAvalable(self.kiwoom.maesu_start_time,
                                        self.kiwoom.maesu_end_time):
            logger.debug("trade_stocks_1")
            hoga_lookup = {'지정가': "00", '시장가': "03"}
            f = open(self.kiwoom.buy_loc, 'rt', encoding='UTF-8')
            buy_list = f.readlines()
            logger.debug("trade_stocks_2")
            f.close()
            code = ''
            for stock in buy_list:
                code = code + stock.split(";")[1] + ";"

            if code != '':
                fidList = str(jk_util.name_fid["현재가"]) + ";" + str(
                    jk_util.name_fid["종목명"]) + ";" + str(
                        jk_util.name_fid["종목코드"])
                self.kiwoom.setRealReg("0101", code[:-1], fidList, "0")
            logger.debug("trade_stocks_3")
            f = open(self.kiwoom.sell_loc, 'rt', encoding='UTF-8')
            sell_list = f.readlines()
            f.close()

            account = self.comboBox.currentText()
            logger.debug("trade_stocks_4")
            if len(buy_list) == 0:
                print("매수 대상 종목이 존재하지 않습니다.")
            logger.debug("trade_stocks_5")
            # buy list
            for row_data in buy_list:
                split_row_data = row_data.split(';')
                hoga = split_row_data[2]
                code = split_row_data[1]
                num = split_row_data[3]
                price = split_row_data[4]
                if split_row_data[-1].rstrip() == '매수전':
                    logger.debug("trade_stocks_6")
                    if self.trade_buy_stratagic(code):  # * 매수전략 적용 *
                        logger.debug("trade_stocks_7")
                        # 다시 해당 주식의 TR정보를 가져옮.. 상한가 오류로 인하여..
                        self.get_current_info_tr(code)
                        if self.get_boyou_cnt() >= total_boyou_cnt:
                            print("보유 종목이 3개 이상 입니다.")
                        else:
                            buy_num_info = self.stratagy.get_buy_num_price(
                                total_buy_money, self.kiwoom.high_price,
                                self.kiwoom.cur_price)
                            num = buy_num_info[0]
                            price = buy_num_info[1]
                            print("매수수량 : ", num, " 매수상한가 : ", price)
                            logger.debug("trade_stocks_8")
                            self.kiwoom.send_order("send_order_req", "0101",
                                                   account, 1, code, num,
                                                   price, hoga_lookup[hoga],
                                                   "")  # 1: 매수, 2: 매도
                            logger.debug("trade_stocks_9")
                            if self.kiwoom.order_result == 0:
                                self._file_update(self.kiwoom.buy_loc, code,
                                                  '매수전', '주문완료')
                            else:
                                print(self.kiwoom.order_result,
                                      ': 매수 처리 못했습니다.')
                # time.sleep(5)
            logger.debug("trade_stocks_10")
            if len(sell_list) == 0:
                print("매도 대상 종목이 존재하지 않습니다.")
            logger.debug("trade_stocks_11")
            # sell list
            for row_data in sell_list:
                split_row_data = row_data.split(';')
                hoga = split_row_data[2]
                code = split_row_data[1]
                num = split_row_data[3]
                price = split_row_data[4]
                logger.debug("trade_stocks_12")
                if split_row_data[-2].rstrip() == '매도전':
                    logger.debug("trade_stocks_13")
                    self.kiwoom.send_order("send_order_req", "0101", account,
                                           2, code, num, price,
                                           hoga_lookup[hoga],
                                           "")  # 1: 매수, 2: 매도
                    print('결과 : ', self.kiwoom.order_result)
                    if self.kiwoom.order_result == 0:
                        self._file_update(self.kiwoom.sell_loc, code, '매도전',
                                          '주문완료')
                    else:
                        print(self.kiwoom.order_result, ': 매도 처리 못했습니다.')
Example #24
0
    def __init__(self):
        super().__init__()
        self.setupUi(self)
        t = check_logger.check_server()  #0.4.5

        self.tr = 0  #총TR요청횟수

        #텔레그램봇
        my_token = '692301814:AAEfmddhyZPcO0Uzh8r5ZehfooTPOvKOOqc'
        self.mybot = telegram.Bot(token=my_token)
        self.chat_id = 544924927

        self.kiwoom = Kiwoom()  #키움인스턴스 생성
        self.kiwoom.comm_connect()  #API로그인

        self.ts_1_p = 'False'  #거래전략1 초기값
        self.market_start = 'false'  #마켓 초기값
        self.market_close = 'false'
        self.shutdown_0900 = 'false'
        self.shutdown_1530 = 'false'

        # Timer1
        self.timer = QTimer(self)
        self.timer.start(1000)  #1초 상태바
        self.timer.timeout.connect(self.timeout)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 25)  #25초 잔고조회
        self.timer2.timeout.connect(self.timeout2)

        # Timer3
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 30)  #30초 매수전략1
        self.timer3.timeout.connect(self.timeout3)

        # Timer4
        self.timer4 = QTimer(self)
        self.timer4.start(1000 * 33)  # 33초 매도전략
        self.timer4.timeout.connect(self.timeout4)

        # Timer5
        self.timer5 = QTimer(self)
        self.timer5.start(1000 * 15)  # 60초 09:00~15:30 장중모드
        self.timer5.timeout.connect(self.timeout5)

        # Timer7
        self.timer7 = QTimer(self)
        self.timer7.start(1000 * 1800)  # 30분 중간보고, 장마감후 어플 및 컴퓨터 종료
        self.timer7.timeout.connect(self.timeout7)

        self.list700 = []
        self.list600 = []
        self.buy_list = []
        self.sell_list = []

        #버튼, 이벤트발생
        self.lineEdit.textChanged.connect(self.code_changed)  #종목코드 입력시
        self.pushButton.clicked.connect(self.send_order)  #현금주문 버튼 클릭시
        self.pushButton_2.clicked.connect(self.check_balance)  #계좌정보 조회
        self.pushButton_3.clicked.connect(self.trading_strategy_1)  #거래전략1호
        self.pushButton_4.clicked.connect(self.quit_app)  #앱종료
        self.pushButton_4.clicked.connect(
            QCoreApplication.instance().quit)  # 앱종료
        self.pushButton_5.clicked.connect(self.timeout7)  # 테스트버튼

        #계좌정보
        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        #프로그램시작알림
        log.info('프로그램이 시작되었습니다.')
        self.textEdit.append(
            '\n' +
            QDateTime.currentDateTime().toString("yyyy/MM/dd\nhh:mm:ss") +
            "ㅣ 프로그램이 시작되었습니다.")
        self.mybot.sendMessage(
            self.chat_id,
            text='\n' +
            QDateTime.currentDateTime().toString("yyyy/MM/dd\n hh:mm:ss") +
            "ㅣ 프로그램이 시작되었습니다.")
        self.get_etf_etn_list()  # ETN, ETF 종목 리스트 저장
Example #25
0
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False  # 자동 trading False이면 작동

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()
        # 전략
        self.stratagy = SysStratagy()

        # Timer1
        self.timer = QTimer(self)
        self.timer.start(1000 * 5)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)

        # Timer3
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 10)

        # Timer4 손절처리를 위한 Timer 설정
        self.timer4 = QTimer(self)
        self.timer4.start(1000 * 60)

        # Naver에서 현재가 가져오기
        self.timer_naver = QTimer(self)
        self.timer_naver.start(1000 * 4)

        # Naver에서 현재가 가져오기
        self.timer_rate = QTimer(self)
        self.timer_rate.start(1000 * 3)

        # 계좌정보 넣어줌
        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        # 보유 종목정보
        self.boyou_stock_list = []
        self.check_balance()
        self.init_boyou_stock_list = self.kiwoom.opw00018_output['multi']
        self.boyou_stock_list = self.init_boyou_stock_list
        # self.boyou_stock_list.append(['삼성전자', '100', '40000', '42000', '200000', '5', '005930'])
        # 아침에 보유주식 매도기능 주석처리함.. 보유주식 정보에서 처리하면 되므로 2019.05.19
        # 보유 주식 매도 주문 아침9시전에 구동시에 보유주식에 대한 매도주문처리
        # self.init_boyou_mado()

        # 매도/매수 리스트 조회
        self.load_buy_sell_list()

        # 보유주식정보 json으로 저장
        self.boyoustock = BoyouStock()
        self.boyou_stock_save_json()

        # 이벤트 정보 연결
        self.timer.timeout.connect(self.timeout)
        self.timer2.timeout.connect(self.timeout2)
        self.timer3.timeout.connect(self.timeout3)
        self.timer4.timeout.connect(
            self.timeout4)  # stop loss 처리 # 보유주식정보 가져오는 것으로 수정함.2019.05.19
        self.timer_naver.timeout.connect(self.timeout_naver)
        self.timer_rate.timeout.connect(self.timeout_rate)
        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(
            self.check_balance_Widget
        )  # pushButton_2 라는 객체가 클릭될 때 check_balance라는 메서드가 호출

        # 손절,익절률 설정 값 읽어오기
        config = self.boyoustock.readConfig()
        if len(config) > 0:
            self.stop_profit_rate = (config["stop_profit_rate"] / 100) + 1
            self.stop_loss_rate = 1 - (config["stop_loss_rate"] / 100)
            self.spinBox_6.setValue(config["stop_profit_rate"])
            self.spinBox_7.setValue(config["stop_loss_rate"])
        else:
            self.stop_profit_rate = (self.spinBox_6.value() / 100) + 1
            self.stop_loss_rate = 1 - (self.spinBox_7.value() / 100)
        print("초기 설정 익절률: " + str(self.stop_profit_rate))
        print("초기 설정 손절률: " + str(self.stop_loss_rate))
Example #26
0
import sys
from PyQt5.QtWidgets import *
import Kiwoom

# 자동로그인 및 종목 데이터 호출 세팅
app = QApplication(sys.argv)
kiwoom = Kiwoom.Kiwoom()
kiwoom.comm_connect()
account_number = kiwoom.get_login_info("ACCNO")
account_number = account_number.split(';')[0]

# 공시에서 받아올 종목 코드
stockcode = '006360'
quantity = 10
signal = "HOLD"
kiwoom.signal(signal, stockcode, account_number, quantity)
Example #27
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False
        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        # Database 연결
        self.con = sqlite3.connect("HBase.db")
        self.cursor = self.con.cursor()

        #보유종목현황 / 선정 종목 버튼 리스트
        self.btn_list1 = []
        self.btn1_num = 0
        self.btn_list2 = []
        self.btn2_num = 0

        #현재 시간을 알려주기 위한 Timer
        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        #실시간 잔고 및 보유종목 현황을 보여주기 위한 Timer
        self.timer2 = QTimer(self)
        self.timer.start(5000)
        self.timer.timeout.connect(self.timeout2)

        #종목코드 입력
        self.lineEdit.textChanged.connect(self.code_change)
        #계좌번호 출력
        accounts_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accounts_num]
        self.comboBox.addItems(accounts_list)
        #주문버튼 / 잔고 조회 버튼
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)
        #선정 종목 정보 출력
        self.load_buy_sell_list()

        #self.kiwoom._set_real_reg("6000", "8121773611", "8019", "0") //실시간 정보 확인

    #프로그램 상에서 수동 주문하는 함수 -> 주문 정보를 DB에 저장
    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        #프로그램 상에서 텍스트 박스 상의 정보를 이용하여 주문
        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        current_time = QTime.currentTime().toString()
        now = datetime.now()
        current_date = str(now.year) + '-' + str(now.month) + '-' + str(
            now.day)

        #구매 정보 DB에 저장
        if order_type == '신규매수':
            sql = "INSERT INTO buy_inform VALUES("
            sql = sql + "'" + current_date + "'" + "," + "'" + current_time + "'" + "," + "'" + name + "'" + "," + "'" + code + "'" + "," + "'수동주문'" + ")"
            self.cursor.execute(sql)
            self.con.commit()
        elif order_type == '신규매도':
            sql = "INSERT INTO sell_inform VALUES("
            #buy_inform 에서 데이터가져오기  // 매수 정보에서 불러온 정보와 더불어 매도 정보에 저장
            df = pd.read_sql("SELECT * FROM buy_inform",
                             self.con,
                             index_col=None)
            df_num = len(df)

            for i in range(df_num - 1, -1, -1):
                if df.loc[i, "종목명"] == name:
                    buy_date = df.loc[i, "매수날짜"]
                    buy_time = df.loc[i, "매수시각"]
                    buy_reason = df.loc[i, "매수근거"]
                    break

            #보유종목현황에서 데이터가져오기
            item_count = len(self.kiwoom.opw00018_output['multi'])
            for j in range(item_count):
                row = self.kiwoom.opw00018_output['multi'][j]
                if row[0] == name:
                    sql = sql + "'" + buy_date + "','" + buy_time + "','" + current_date + "','" + current_time + "','" + row[
                        0] + "','" + row[1] + "','" + row[2] + "','" + row[
                            3] + "','" + row[4] + "','" + row[5] + "','" + row[
                                6] + "','" + row[
                                    7] + "','" + buy_reason + "'," + "'수동주문'" + ")"
                    #delete_sql = "DELETE FROM buy_inform WHERE 종목명 = "
                    #delete_sql = delete_sql + "'" + name + "'"
                    self.cursor.execute(sql)
                    #self.cursor.execute(delete_sql)
                    self.con.commit()
                    break
        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")

    def code_change(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def timeout(self):
        market_start_time = QTime(9, 0, 0)
        current_time = QTime.currentTime()

        if current_time > market_start_time and self.trade_stocks_done is False:
            self.trade_stocks()
            self.trade_stocks_done = True

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    #종목번호를 누르면 네이버,다음 증권 정보를 불러옴
    def link_btn(self):
        naver_url = "https://finance.naver.com/item/fchart.nhn?code="
        daum_url = "https://finance.daum.net/quotes/"
        sender = self.sender()
        code = sender.text()
        daum_url = daum_url + "A" + code + "#chart"
        webbrowser.open_new(daum_url)
        code = re.findall('\d+', code)[0]
        naver_url = naver_url + code
        webbrowser.open_new(naver_url)

    #현재 보유하고 있는 주식과 잔고를 보여주는 함수
    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        #opw00018 - 각 종목에 대한 비중, 매입가, 평가액 등을 요청
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        #opw00001 - 이틀 뒤의 예수금을 보여줌
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        #balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        #Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)
        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                if i == 1:
                    self.btn_list1.append(QPushButton(self.tableWidget_2))
                    self.btn_list1[self.btn1_num].setText(row[i])
                    self.btn_list1[self.btn1_num].clicked.connect(
                        self.link_btn)
                    self.tableWidget_2.setCellWidget(
                        j, i, self.btn_list1[self.btn1_num])
                    self.btn1_num += 1
                else:
                    item = QTableWidgetItem(row[i])
                    item.setTextAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
                    self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()

    #매수해야 하는 목록, 매도해야 하는 목록을 불러와 표로 보여주는 함수
    def load_buy_sell_list(self):
        f = open("buy_list.txt", 'rt', encoding='UTF8')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt', encoding='UTF8')
        sell_list = f.readlines()
        f.close()

        row_count = len(buy_list) + len(sell_list)
        self.tableWidget_3.setRowCount(row_count)

        #buy list
        for j in range(len(buy_list)):
            row_data = buy_list[j]
            split_row_data = row_data.split(';')

            for i in range(len(split_row_data)):
                if i == 1:
                    self.btn_list2.append(QPushButton(self.tableWidget_2))
                    self.btn_list2[self.btn2_num].setText(
                        split_row_data[i].rstrip())
                    self.btn_list2[self.btn2_num].clicked.connect(
                        self.link_btn)
                    self.tableWidget_3.setCellWidget(
                        j, i, self.btn_list2[self.btn2_num])
                    self.btn2_num += 1
                else:
                    item = QTableWidgetItem(split_row_data[i].rstrip())
                    item.setTextAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
                    self.tableWidget_3.setItem(j, i, item)

        #sell list
        for j in range(len(sell_list)):
            row_data = sell_list[j]
            split_row_data = row_data.split(';')

            for i in range(len(split_row_data)):
                if i == 1:
                    self.btn_list2.append(QPushButton(self.tableWidget_2))
                    self.btn_list2[self.btn2_num].setText(
                        split_row_data[i].rstrip())
                    self.btn_list2[self.btn2_num].clicked.connect(
                        self.link_btn)
                    self.tableWidget_3.setCellWidget(
                        len(buy_list) + j, i, self.btn_list2[self.btn2_num])
                    self.btn2_num += 1
                else:
                    item = QTableWidgetItem(split_row_data[i].rstrip())
                    item.setTextAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
                    self.tableWidget_3.setItem(len(buy_list) + j, i, item)

        self.tableWidget_3.resizeRowsToContents()

    #현재 작성되어 있는 매수해야하는 목록과 매도해야 하는 목록을 바탕으로 매수,매도 진행
    def trade_stocks(self):
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        f = open("buy_list.txt", 'rt', encoding='UTF8')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt', encoding='UTF8')
        sell_list = f.readlines()
        f.close()

        #acoount
        account = self.comboBox.currentText()

        #Current Time and Date Check
        current_time = QTime.currentTime().toString()
        now = datetime.now()
        current_date = str(now.year) + '-' + str(now.month) + '-' + str(
            now.day)

        #buy list
        for row_data in buy_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[3]
            code = split_row_data[1]
            name = split_row_data[2]
            num = split_row_data[4]
            price = split_row_data[5]
            buy_reason = split_row_data[7]

            if split_row_data[6].rstrip() == '매수전':
                sql = "INSERT INTO buy_inform VALUES("
                sql = sql + "'" + current_date + "'" + "," + "'" + current_time + "'" + "," + "'" + name + "'" + "," + "'" + code + "','" + buy_reason + "')"
                self.cursor.execute(sql)
                self.con.commit()
                self.kiwoom.send_order("send_order_req", "0101", account, 1,
                                       code, num, price, hoga_lookup[hoga], "")

        #sell list
        for row_data in sell_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[3]
            code = split_row_data[1]
            name = split_row_data[2]
            num = split_row_data[4]
            price = split_row_data[5]
            sell_reason = split_row_data[7]

            if split_row_data[6].rstrip() == '매도전':
                sql = "INSERT INTO sell_inform VALUES("
                # buy_inform 에서 데이터가져오기
                df = pd.read_sql("SELECT * FROM buy_inform",
                                 self.con,
                                 index_col=None)
                df_num = len(df)
                for i in range(df_num - 1, -1, -1):
                    if df.loc[i, "종목명"] == name:
                        buy_date = df.loc[i, "매수날짜"]
                        buy_time = df.loc[i, "매수시각"]
                        buy_reason = df.loc[i, "매수근거"]
                        break

                # 보유종목현황에서 데이터가져오기
                item_count = len(self.kiwoom.opw00018_output['multi'])
                for j in range(item_count):
                    row = self.kiwoom.opw00018_output['multi'][j]
                    if row[0] == name:
                        sql = sql + "'" + buy_date + "','" + buy_time + "','" + current_date + "','" + current_time + "','" + \
                              row[0] + "','" + row[1] + "','" + row[2] + "','" + row[3] + "','" + row[4] + "','" + row[
                                  5] + "','" + row[6] + "','" + row[7] + "','" + buy_reason + "','" + sell_reason + "')"
                        # delete_sql = "DELETE FROM buy_inform WHERE 종목명 = "
                        # delete_sql = delete_sql + "'" + name + "'"
                        self.cursor.execute(sql)
                        # self.cursor.execute(delete_sql)
                        self.con.commit()
                        break

                self.kiwoom.send_order("send_order_req", "0101", account, 2,
                                       code, num, price, hoga_lookup[hoga], "")

        #buy / sell list replace
        for i, row_data in enumerate(buy_list):
            buy_list[i] = buy_list[i].replace("매수전", "주문완료")

        for i, row_data in enumerate(sell_list):
            sell_list[i] = sell_list[i].replace("매도전", "주문완료")

        #file update
        f = open("buy_list.txt", 'wt', encoding='UTF8')
        for row_data in buy_list:
            f.write(row_data)
        f.close()

        f = open("sell_list.txt", 'wt', encoding='UTF8')
        for row_data in sell_list:
            f.write(row_data)
        f.close()
Example #28
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.trade_stocks_done = False

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.timer2 = QTimer(self)
        self.timer2.start(1000 *10)
        self.timer2.timeout.connect(self.timeout2)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        self.pushButton_2.clicked.connect(self.check_balance)

        self.load_buy_sell_list()

    def trade_stocks(self):
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt')
        sell_list = f.readlines()
        f.close()

        # account
        account = self.comboBox.currentText()

        # buy list
        for row_data in buy_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[2]
            code = split_row_data[1]
            num = split_row_data[3]
            price = split_row_data[4]

            if split_row_data[-1].rstrip() == '매수전':
                self.kiwoom.send_order("send_order_req", "0101", account, 1, code, num, price, hoga_lookup[hoga], "")

        # sell list
        for row_data in sell_list:
            split_row_data = row_data.split(';')
            hoga = split_row_data[2]
            code = split_row_data[1]
            num = split_row_data[3]
            price = split_row_data[4]

            if split_row_data[-1].rstrip() == '매도전':
                self.kiwoom.send_order("send_order_req", "0101", account, 2, code, num, price, hoga_lookup[hoga], "")

        # buy list
        for i, row_data in enumerate(buy_list):
            buy_list[i] = buy_list[i].replace("매수전", "주문완료")

        # file update
        f = open("buy_list.txt", 'wt')
        for row_data in buy_list:
            f.write(row_data)
        f.close()

        # sell list
        for i, row_data in enumerate(sell_list):
            sell_list[i] = sell_list[i].replace("매도전", "주문완료")

        # file update
        f = open("sell_list.txt", 'wt')
        for row_data in sell_list:
            f.write(row_data)
        f.close()

    def load_buy_sell_list(self):
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        f = open("sell_list.txt", 'rt')
        sell_list = f.readlines()
        f.close()

        row_count = len(buy_list) + len(sell_list)
        self.tableWidget_4.setRowCount(row_count)

        # buy list
        for j in range(len(buy_list)):
            row_data = buy_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(split_row_data[1].rsplit())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_4.setItem(j, i, item)

        # sell list
        for j in range(len(sell_list)):
            row_data = sell_list[j]
            split_row_data = row_data.split(';')
            split_row_data[1] = self.kiwoom.get_master_code_name(split_row_data[1].rstrip())

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_4.setItem(len(buy_list) + j, i, item)

        self.tableWidget_4.resizeRowsToContents()

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account, order_type_lookup[order_type], code, num, price, hoga_lookup[hoga], "")

    def timeout(self):
        market_start_time = QTime(9, 0, 0)
        current_time = QTime.currentTime()

        if current_time > market_start_time and self.trade_stocks_done is False:
            self.trade_stocks()
            self.trade_stocks_done = True

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i - 1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
Example #29
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 10)
        self.timer2.timeout.connect(self.timeout2)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.cmbAccountList.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.btnSendOrder.clicked.connect(self.send_order)
        self.btnCheckBalance.clicked.connect(self.check_balance)

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account,
                               order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.chkRealTime.isChecked():
            self.check_balance()

    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)
        self.token = ""

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.code = '093320'
        self.name = self.kiwoom.get_master_code_name(self.code)
        self.kiwoom.current = {}

        self.past_price = 0
        self.past_ratio = 0
        self.past_amount = 0

        # Timer1 - 1초에 한 번씩 이벤트가 발생한다.
        self.timer = QTimer(self)
        self.timer.start(1000 * 15)
        self.timer.timeout.connect(self.timeout_visualize)

        self.timer = QTimer(self)
        self.timer.start(1000 * 30)
        self.timer.timeout.connect(self.timeout_message)

    def request_data(self, code):
        """
        데이터 요청

        :param code:
        :return:
        """
        self.kiwoom.current = {}
        self.kiwoom.set_input_value("종목코드", code)
        self.kiwoom.comm_rq_data("opt10001_req", 'opt10001', 0, '2000')

    def timeout_visualize(self):
        """
        30초마다 서버로부터 가격, 상승률, 양을 가져온다.

        :return:
        """
        current_time = QTime.currentTime()

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

        self.request_data(self.code)
        self.lineEdit.setText(self.kiwoom.get_master_code_name(self.code))
        self.lineEdit_2.setText(self.kiwoom.current['price'])
        self.lineEdit_3.setText(self.kiwoom.current['ratio'])
        self.lineEdit_4.setText(self.kiwoom.current['amount'])

    def timeout_message(self):
        """
        60초마다 변경 사항이 있을 시 텔레그램 메세지를 보낸다.

        :return:
        """
        bot = telegram.Bot(token=self.token)
        chat_id = bot.getUpdates()[-1].message.chat.id

        price = self.kiwoom.current['price']
        ratio = self.kiwoom.current['ratio']
        amount = self.kiwoom.current['amount']

        if self.past_price != price:
            message = self.name + "\n" + \
                  "현재 가격: " + price + "\n" + \
                  "등락율: " + ratio + "%\n" + \
                  "거래량: " + amount + "\n"
            bot.sendMessage(chat_id=chat_id, text=message)

            self.past_price = price
            self.past_ratio = ratio
            self.past_amount = amount
        """try:
            print("window check")
            print(self.activeModalWidget())
            dialog = self.activeModalWidget()
            if dialog is not None:
                self.kiwoom.comm_terminate()
                self.kiwoom = None

        except Exception as e:
            print(e)"""


if __name__ == "__main__":
    app = StockApplication(sys.argv)
    app.setupSignals()
    StockApplication.kiwoom = Kiwoom.Kiwoom()
    StockApplication.kiwoom.comm_connect()

    kospi_codes = StockApplication.kiwoom.get_code_list_by_market(0)
    start = 0
    num = len(kospi_codes)
    bound = range(start, num)

    print(bound)

    for i in bound:

        code = kospi_codes[i]
        StockApplication.kiwoom.reset_opt10001_output()
        StockApplication.kiwoom.set_input_value("종목코드", code)
        StockApplication.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0,
Example #32
0
 def __init__(self):
     self.kiwoom = Kiwoom()
     self.kiwoom.comm_connect()
     self.get_code_list()
     self.excelfile_initiator()
Example #33
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        self.timer = QTimer(self)
        self.timer.start(500)
        self.timer.timeout.connect(self.timeout)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")

        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        self.lineEdit.textChanged.connect(self.code_changed)
        self.pushButton.clicked.connect(self.send_order)
        
        ## 조건검색식 관련 추가
        self.load_condition_list()
        self.checkBox_cond.setChecked(True)
        self.pushButton_cond.clicked.connect(self.start_cond)

    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account, order_type_lookup[order_type], code, num, price, hoga_lookup[hoga], "")

    def timeout(self):
        current_time = QTime.currentTime()
        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

        if self.kiwoom.msg:
            # 텔레그램
            if self.checkBox_cond.isChecked():
                self.kiwoom.bot.sendMessage(chat_id=self.kiwoom.chat_id, text=self.kiwoom.msg)
            self.textEdit_cond.append(self.kiwoom.msg)
            self.kiwoom.msg = ""

    ## 조건검색식 관련 추가
    def load_condition_list(self):
        print("pytrader.py [load_condition_list]")
        """ condiComboBox에 condition List를 설정한다. """

        cond_list = []
        try:
            # 조건식 실행
            self.kiwoom.getConditionLoad()
            # getConditionLoad 가 정상 실행되면 kiwoom.condition에 조건식 목록이 들어간다.
            dic = self.kiwoom.condition
            
            for key in dic.keys():
                cond_list.append("{};{}".format(key, dic[key]))
            
            # 콤보박스에 조건식 목록 추가
            self.comboBox_cond.addItems(cond_list)

        except Exception as e:
            print(e)

    def start_cond(self):
        conditionIndex = self.comboBox_cond.currentText().split(';')[0]
        conditionName = self.comboBox_cond.currentText().split(';')[1]

        if self.pushButton_cond.text() == "적용":

            try: 
                self.kiwoom.sendCondition("0",conditionName,int(conditionIndex),1)
                self.pushButton_cond.setText("해제")
                self.comboBox_cond.setEnabled(False)
                self.checkBox_cond.setEnabled(False)
                print("{} activated".format(conditionName))

            except Exception as e:
                print(e)

        else:
            self.kiwoom.sendConditionStop("0",conditionName,conditionIndex)
            self.pushButton_cond.setText("적용")
            self.comboBox_cond.setEnabled(True)
            self.checkBox_cond.setEnabled(True)
Example #34
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

        self.tr = 0  # 총TR요청횟수

        # 텔레그램봇
        my_token = '692301814:AAEfmddhyZPcO0Uzh8r5ZehfooTPOvKOOqc'
        self.mybot = telegram.Bot(token=my_token)
        self.chat_id = 544924927

        self.kiwoom = Kiwoom()  # 키움인스턴스 생성
        self.kiwoom.comm_connect()  # API로그인

        self.ts_1_p = 'False'  # 거래전략1 초기값
        self.market_start = 'false'  # 마켓 초기값
        self.market_close = 'false'
        self.shutdown_0900 = 'false'
        self.shutdown_1530 = 'false'

        # 0.4.6
        t = time.gmtime()
        self.file_today = '{}-{}-{}'.format(t.tm_year, t.tm_mon, t.tm_mday)

        # Timer1
        self.timer = QTimer(self)
        self.timer.start(1000)  # 1초 상태바
        self.timer.timeout.connect(self.timeout)

        # Timer2
        self.timer2 = QTimer(self)
        self.timer2.start(1000 * 25)  # 25초 잔고조회
        self.timer2.timeout.connect(self.timeout2)

        # Timer3
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 30)  # 30초 매수전략1
        self.timer3.timeout.connect(self.timeout3)

        # Timer4
        self.timer4 = QTimer(self)
        self.timer4.start(1000 * 33)  # 33초 매도전략
        self.timer4.timeout.connect(self.timeout4)

        # Timer5
        self.timer5 = QTimer(self)
        self.timer5.start(1000 * 15)  # 60초 09:00~15:30 장중모드
        self.timer5.timeout.connect(self.timeout5)

        # Timer7
        self.timer7 = QTimer(self)
        self.timer7.start(1000 * 1800)  # 30분 중간보고, 장마감후 어플 및 컴퓨터 종료
        self.timer7.timeout.connect(self.timeout7)

        self.list700 = []
        self.list600 = []
        self.buy_list = []
        self.sell_list = []

        # 버튼, 이벤트발생
        self.lineEdit.textChanged.connect(self.code_changed)  # 종목코드 입력시
        self.pushButton.clicked.connect(self.send_order)  # 현금주문 버튼 클릭시
        self.pushButton_2.clicked.connect(self.check_balance)  # 계좌정보 조회
        self.pushButton_3.clicked.connect(self.trading_strategy_1)  # 거래전략1호
        self.pushButton_4.clicked.connect(self.quit_app)  # 앱종료
        self.pushButton_4.clicked.connect(QCoreApplication.instance().quit)  # 앱종료
        self.pushButton_5.clicked.connect(self.timeout7)  # 테스트버튼

        # 계좌정보
        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]
        self.comboBox.addItems(accounts_list)

        # 프로그램시작알림
        log.info('프로그램이 시작되었습니다.')
        self.textEdit.append('\n' + QDateTime.currentDateTime().toString("yyyy/MM/dd\nhh:mm:ss") + "ㅣ 프로그램이 시작되었습니다.")
        self.mybot.sendMessage(self.chat_id, text='\n' + QDateTime.currentDateTime().toString(
            "yyyy/MM/dd\n hh:mm:ss") + "ㅣ 프로그램이 시작되었습니다.")
        self.get_etf_etn_list()  # ETN, ETF 종목 리스트 저장

    # 종료
    def quit_app(self):
        log.info('프로그램이 종료되었습니다.')
        if self.ts_1_p == 'True':
            self.trading_strategy_1()
        self.timer.stop()
        self.timer2.stop()
        self.timer3.stop()
        self.timer4.stop()
        self.timer5.stop()
        self.timer7.stop()
        time.sleep(1)

        # 계좌정보요청
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        mystocks = ''

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        self.tr += 1
        bb = self.kiwoom.opw00018_output['single']
        myaccount = '총매입금액: %s원\n총평가금액: %s원\n총평가손익금액: %s원\n총수익률(%%): %s\n추정예탁자산: %s원' % (
        bb[0], bb[1], bb[2], bb[3], bb[4])

        a = len(self.kiwoom.opw00018_output['multi'])
        if a != 0:
            name = []
            num = []
            buy = []
            price = []
            earn = []
            ret = []
            for i in range(a):
                name.append(self.kiwoom.opw00018_output['multi'][i][0])
                num.append(self.kiwoom.opw00018_output['multi'][i][1])
                buy.append(self.kiwoom.opw00018_output['multi'][i][2])
                price.append(self.kiwoom.opw00018_output['multi'][i][3])
                earn.append(self.kiwoom.opw00018_output['multi'][i][4])
                ret.append(self.kiwoom.opw00018_output['multi'][i][5])
            mystocks = {'종목': name, '수량': num, '매입가': buy, '현재가': price, '평가손익': earn, '수익률(%)': ret}
            mystocks = DataFrame(mystocks)
            mystocks = mystocks.set_index(['종목'])

        # last 보고
        self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 프로그램이 종료되었습니다.")
        self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString(
            "hh:mm:ss") + "ㅣ 프로그램이 종료되었습니다.\n총 TR 요청 횟수 : %d회\n --------계좌현황--------\n계좌번호: %s\n%s\n --------보유종목--------\n%s"
                                                  % (self.tr, account_number, myaccount, mystocks))
        with open('log.txt', 'a') as f:
            f.writelines(self.textEdit.toPlainText())
        time.sleep(3)

    # 상태표시줄(현재시간, 서버연결상태)
    def timeout(self):
        market_start_time = QTime(9, 00, 00)
        market_close_time = QTime(15, 30, 00)
        market_start_time2 = QTime(9, 00, 2)
        market_close_time2 = QTime(15, 30, 2)
        current_time = QTime.currentTime()

        # 9시 이후에 급등주알고리즘 시작
        if current_time > market_start_time and current_time < market_start_time2 and self.market_start == 'false':
            log.info('장 시작 알림')
            self.market_start = 'true'
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 장이 시장되었습니다.")
            self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 장이 시작되었습니다.")
        elif current_time > market_close_time and current_time < market_close_time2 and self.market_close == 'false':
            log.info('장 종료알림')
            self.market_close = 'true'
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 장이 종료되었습니다.")
            self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 장이 종료되었습니다.")

        text_time = current_time.toString("hh:mm:ss")
        time_msg = "현재시간: " + text_time

        state = self.kiwoom.GetConnectState()
        if state == 1:
            state_msg = "서버가 연결되었습니다."
        else:
            state_msg = "서버가 연결되지 않았습니다."
            log.fatal('서버 미연결')
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ서버가 연결되지 않았습니다.")
            self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 서버가 연결되지 않았습니다.")

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout2(self):
        if self.checkBox.isChecked():
            self.check_balance()  # 계좌정보 실시간 조회

    def timeout3(self):
        if self.ts_1_p == 'True':  # 매수전략1 진행시 30초마다 조회
            log.debug('거래량조회 알고리즘 실행')
            self.volume_check()

    def timeout4(self):
        log.debug('매도 알고리즘 실행')
        self.sell_stocks()  # 매도전략


    def timeout5(self): #체크시 9시~15:30까지 작동

        if self.checkBox_2.isChecked():

            market_start_time = QTime(9, 1, 30)
            market_close_time = QTime(15, 40, 00)
            current_time = QTime.currentTime()

            # 9시 이후에 급등주알고리즘 시작
            if current_time > market_start_time and self.shutdown_0900 == 'false' and self.ts_1_p == 'False':
                log.info('장이 시작되어 매수알고리즘 실행')
                self.shutdown_0900 = 'true'
                self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 장 시작, 매수전략1 시작하겠습니다.")
                self.mybot.sendMessage(self.chat_id,
                                       text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 장 시작, 매수전략1 시작하겠습니다.")
                self.trading_strategy_1()

            # 15시 40 분 이후 알고리즘 중지 및 10분 뒤 컴퓨터 종료
            elif current_time > market_close_time and self.shutdown_1530 == 'false':
                log.info('장이 종료되어 알고리즘 중지')
                self.shutdown_1530 = 'true'
                self.trading_strategy_1()
                time.sleep(1)
                self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 10분 후 컴퓨터를 종료합니다.")
                self.mybot.sendMessage(self.chat_id,
                                       text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 10분 후 컴퓨터를 종료합니다.")
                log.fatal('컴퓨터 종료 카운트 시작')

                self.quit_app()
                time.sleep(10)
                os.system("shutdown -s -t 600")
                print('10분 후 컴퓨터를 종료합니다...')

    def timeout7(self):  # 중간보고
        log.debug('중간보고')
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        self.tr += 1
        mystocks = ''
        bb = self.kiwoom.opw00018_output['single']
        myaccount = '총매입금액: %s원\n총평가금액: %s원\n총평가손익금액: %s원\n총수익률(%%): %s\n추정예탁자산: %s원' % (
        bb[0], bb[1], bb[2], bb[3], bb[4])
        print(myaccount)
        a = len(self.kiwoom.opw00018_output['multi'])
        if a != 0:
            name = []
            num = []
            buy = []
            price = []
            earn = []
            ret = []
            for i in range(a):
                name.append(self.kiwoom.opw00018_output['multi'][i][0])
                num.append(self.kiwoom.opw00018_output['multi'][i][1])
                buy.append(self.kiwoom.opw00018_output['multi'][i][2])
                price.append(self.kiwoom.opw00018_output['multi'][i][3])
                earn.append(self.kiwoom.opw00018_output['multi'][i][4])
                ret.append(self.kiwoom.opw00018_output['multi'][i][5])
            mystocks = {'종목': name, '수량': num, '매입가': buy, '현재가': price, '평가손익': earn, '수익률(%)': ret}
            mystocks = DataFrame(mystocks)
            mystocks = mystocks.set_index(['종목'])
        print(mystocks)
        time.sleep(1)
        # 중간보고
        self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 중간보고 완료.")
        self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString("hh:mm:ss") +
                                                  "\n--------중간보고--------\n총 TR 요청 횟수 : %d회\n --------계좌현황--------\n계좌번호: %s\n%s\n --------보유종목--------\n%s"
                                                  % (self.tr, account_number, myaccount, mystocks))

    # 종목명 나타내기
    def code_changed(self):
        code = self.lineEdit.text()
        name = self.kiwoom.get_master_code_name(code)
        self.lineEdit_2.setText(name)

    # 현금주문(수동주문)
    def send_order(self):
        order_type_lookup = {'신규매수': 1, '신규매도': 2, '매수취소': 3, '매도취소': 4}
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        account = self.comboBox.currentText()
        order_type = self.comboBox_2.currentText()
        code = self.lineEdit.text()
        hoga = self.comboBox_3.currentText()
        num = self.spinBox.value()
        price = self.spinBox_2.value()

        self.kiwoom.send_order("send_order_req", "0101", account, order_type_lookup[order_type], code, num, price,
                               hoga_lookup[hoga], "")
        self.tr += 1

    # 계좌정보
    def check_balance(self):
        log.debug('잔고조회')
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")

        self.tr += 1
        # opw00001
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")
        self.tr += 1

        # balance
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        for i in range(1, 6):
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i - 1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)

        self.tableWidget.resizeRowsToContents()

        # Item list
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)

        self.tableWidget_2.resizeRowsToContents()

    # 거래량급증 거래전략1
    def trading_strategy_1(self):
        log.info('매수전략1 실행/중지')
        if self.ts_1_p == 'False':
            log.debug('매수전략1 실행중')
            print('ts_1_p = true, 매수전략1 실행중입니다.')
            self.ts_1_p = 'True'
            self.label_7.setText("진행중...")
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 매수전략1 시작되었습니다.")
            self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 매수전략1 시작되었습니다.")
            self.volume_check()

        elif self.ts_1_p == 'True':
            log.debug('매수전략1 중지')
            print('ts_1_p = False, 매수전략1 중지되었습니다.')
            self.label_7.setText("")
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 매수전략1 중지되었습니다.")
            self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 매수전략1 중지되었습니다.")
            self.ts_1_p = 'False'

    # 매수,매도주문
    def order_stocks(self, bs, code, num, price, set_price):

        '''
        :param bs: 매수=1 매도=2
        :param code: 종목코드
        :param num: 수량
        :param price: 가격 (시장가이면 0)
        :param set_price: 지정가=00 시장가=03
        :return:
        '''
        # 0.4.7 수정 장중에만 주문넣기
        market_start_time = QTime(9, 00, 00)
        market_close_time = QTime(15, 30, 00)
        current_time = QTime.currentTime()

        if current_time > market_start_time and current_time < market_close_time:

            account = self.comboBox.currentText()
            log.critical('order_stocks 주문실행')
            # order
            self.kiwoom.send_order("send_order_req", "0101", account, bs, code, num, price, set_price, "")
            self.tr += 1
            # 0.4.6 리스트 작성

            if bs == 1:  # 매수
                f = open(sys.path[0] + '\\backup\\' + self.file_today + '_buy.txt', 'a')
                f.write(code + '\n')
                f.close()
                log.debug('buy_list.txt 기록')
            elif bs == 2:  # 매도
                f = open(sys.path[0] + '\\backup\\' + self.file_today + '_sell.txt', 'a')
                f.write(code + '\n')
                f.close()
                log.debug('sell_list.txt 기록')
        else:
            log.debug('장이 닫혀있어 주문하지 않았습니다.')
            print('장이 닫혀있어 주문하지 않았습니다.')

    # 거래량급증 조회
    def volume_check(self):

        print('조회수급등조회시작')
        kospi_url = 'https://finance.naver.com/sise/sise_quant_high.nhn'
        kosdaq_url = 'https://finance.naver.com/sise/sise_quant_high.nhn?sosok=1'

        df = pd.DataFrame()

        html_1 = requests.get(kospi_url).text
        df = df.append(pd.read_html(html_1, header=0)[1])
        html_2 = requests.get(kosdaq_url).text
        df = df.append(pd.read_html(html_2, header=0)[1])
        del df['PER']
        df = df.dropna()
        df = df.rename(
            columns={'N': 'num', '증가율': 'rate', '종목명': 'name', '현재가': 'price', '전일비': 'diff', '등락률': 'updown',
                     '매수호가': 'buy_hoga',
                     '매도호가': 'sell_hoga', '거래량': 'volume', '전일거래량': 'yes_volume'})
        df = df.set_index(['num'])  # 크롤링완료
        html = html_1 + html_2
        if df.empty is True:
            log.debug('네이버금융 데이터가 없음')
            self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + 'ㅣ 네이버금융 데이터가 없습니다.')
            self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString(
                'hh:mm:ss') + 'ㅣ 네이버금융 데이터가 없습니다.')
            print('네이버금융 데이터가 없습니다.')
        else:
            # 0.4.6 장 종료시 데이터프레임 저장
            if self.market_close == 'true':
                df.to_csv(sys.path[0] + '\\backup\\' + self.file_today + '_volume.csv', encoding='cp949')

            # 0.4.1 수정
            # 700이상
            df700 = df[[a > 700 for a in df.rate]]
            a700 = list(df700['name'])
            if len(df700) != 0:
                for i in range(len(df700)):
                    # 0.4.3 수정(종목이름 앞글자 같을 때 보완)
                    a = html.find(a700[i])
                    b = len(a700[i])
                    if html[a + b] == '<':
                        code = html[a - 22:a - 16]
                        self.list700.append(code)
                    else:
                        html = html[a + b:]
                        a = html.find(a700[i])
                        code = html[a - 22:a - 16]
                        self.list700.append(code)
            print(self.list700)
            print(self.list600)

            # 교집합 구하기
            aa = set(self.list700)
            bb = set(self.list600)
            buy_set = aa & bb
            buy_set = list(buy_set)
            if len(buy_set) != 0:
                for code in buy_set:
                    if code in self.etn_etf_list:
                        pass
                    else:
                        for i in range(len(buy_set)):
                            self.buy_list.append(buy_set[i])

            # 600~700
            self.list600 = []
            df600 = df[[a < 700 for a in df.rate]]
            a600 = list(df600['name'])
            if len(df600) != 0:
                for i in range(len(df600)):
                    a = html.find(a600[i])
                    b = len(a600[i])
                    if html[a + b] == '<':
                        code = html[a - 22:a - 16]
                        self.list600.append(code)
                    else:
                        html = html[a + b:]
                        a = html.find(a600[i])
                        code = html[a - 22:a - 16]
                        self.list600.append(code)
            print('매수리스트: %s' % self.buy_list)
            log.debug('buy_list 저장완료')

        # order
        # 0.4.3 자산5%
        if len(self.buy_list) == 0:
            pass
        else:
            log.debug('바이리스트 주문을 시작함')
            self.kiwoom.reset_opw00018_output()
            account_number = self.comboBox.currentText()
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")
            buy_q = int(self.kiwoom.opw00018_output['single'][4].replace(',', '')) // 20  # 추정예탁자산의 5%
            self.tr += 1
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")
            d2_deposit = int(self.kiwoom.d2_deposit.replace(',', ''))  # d2 예수금
            self.tr += 1

            if buy_q <= d2_deposit:
                log.critical('주문실행')
                for code in self.buy_list:  # 주문하기
                    # 0.4.3 매수비중 5%제한
                    time.sleep(0.5)
                    self.kiwoom.set_input_value("종목코드", code)
                    self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "0101")
                    buy_q = buy_q // self.kiwoom.stock_pv  # 매수금액/현재가 : 수량
                    self.tr += 1
                    time.sleep(1)
                    self.order_stocks(1, code, buy_q, 0, '03')
                    self.textEdit.append(
                        QTime.currentTime().toString("hh:mm:ss") + 'ㅣ 매수주문\n종목: %s\n수량: %d\n가격: 시장가\n현재가:%s' % (
                            self.kiwoom.stock_name, buy_q, self.kiwoom.stock_pv))
                    self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString(
                        'hh:mm:ss') + 'ㅣ매수주문\n 종목: %s\n수량: %d\n가격: 시장가\n현재가:%s' % (
                                                                  self.kiwoom.stock_name, buy_q, self.kiwoom.stock_pv))


            else:  # 주문x
                log.critical('예수금이 부족해 주문하지 못함')
                self.textEdit.append(QTime.currentTime().toString("hh:mm:ss") + "ㅣ 예수금이 부족합니다.")
                self.mybot.sendMessage(self.chat_id,
                                       text=QTime.currentTime().toString("hh:mm:ss") + "ㅣ 예수금이 부족합니다.")
                print('예수금이 부족합니다.')

        self.buy_list = []
        self.list700 = []
        print("거래량급증조회완료")
        log.debug('거래량급증조회완료')

    # 목표수익률 도달시 팔기
    def sell_stocks(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.comboBox.currentText()
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(1)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        self.tr += 1

        list_1 = list(self.kiwoom.opw00018_output['multi'])
        a = len(list_1)
        if a != 0:
            log.debug('보유종목현황')
            print('보유종목현황: %s' % list_1)
            # 0.4.3 3%, -2.5% 수정
            for i in range(a):
                if float(list_1[i][5]) > 3:

                    code = list_1[i][6]
                    num = int(list_1[i][1].replace('.00', '').replace(',', ''))

                    # 0.4.4 매도주문 1회만 실행
                    if code not in self.sell_list:
                        log.debug('이익실현매도')
                        self.sell_list.append(code)
                        self.order_stocks(2, code, num, 0, '03')
                        print('매도종목: %s' % code)
                        self.kiwoom.set_input_value("종목코드", code)
                        self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "0101")
                        self.tr += 1
                        time.sleep(1)
                        self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString(
                            "hh:mm:ss") + 'ㅣ 이익실현\n매도주문\n 종목: %s\n수량: %d\n가격: 시장가\n현재가: %s' % (
                                                                  self.kiwoom.stock_name, num, self.kiwoom.stock_pv))
                        self.textEdit.append(
                            QTime.currentTime().toString("hh:mm:ss") + 'ㅣ 매도주문\n종목: %s\n수량: %d\n가격: 시장가\n현재가: %s' % (
                            self.kiwoom.stock_name, num, self.kiwoom.stock_pv))
                    else:
                        log.debug('이미 접수된 주문')

                elif float(list_1[i][5]) < -2.5:

                    code = list_1[i][6]
                    num = int(list_1[i][1].replace('.00', '').replace(',', ''))

                    if code not in self.sell_list:
                        log.debug('손절매도')
                        self.sell_list.append(code)
                        self.order_stocks(2, code, num, 0, '03')
                        print('매도종목: %s' % code)
                        self.kiwoom.set_input_value("종목코드", code)
                        self.kiwoom.comm_rq_data("opt10001_req", "opt10001", 0, "0101")
                        self.tr += 1
                        time.sleep(1)
                        self.mybot.sendMessage(self.chat_id, text=QTime.currentTime().toString(
                            "hh:mm:ss") + 'ㅣ 손절\n매도주문\n 종목: %s\n수량: %d\n가격: 시장가\n현재가: %s' % (
                                                                  self.kiwoom.stock_name, num, self.kiwoom.stock_pv))
                        self.textEdit.append(
                            QTime.currentTime().toString("hh:mm:ss") + 'ㅣ 매도주문\n종목: %s\n수량: %d\n가격: 시장가\n현재가: %s' % (
                            self.kiwoom.stock_name, num, self.kiwoom.stock_pv))
                    else:
                        log.debug('이미 접수된 주문')

    # ETF, ETN 종목 리스트 저장
    def get_etf_etn_list(self):
        log.debug('etf,etn리스트 저장')
        time.sleep(2)
        market_list = ['etn', 'etf']
        self.etn_etf_list = []

        for market in market_list:

            if market == 'etn':
                url = 'https://finance.naver.com/api/sise/etnItemList.nhn?'
            elif market == 'etf':
                url = 'https://finance.naver.com/api/sise/etfItemList.nhn?'
            html = requests.get(url).text
            aa = html.split('},')
            for stock in aa:
                code_start = stock.find('itemcode')
                code = stock[code_start + 11:code_start + 17]
                self.etn_etf_list.append(code)
Example #35
0
class MyWindow(QMainWindow, form_class):
    def __init__(self):
        super().__init__()
        self.setupUi(self)
        self.saveditem = Saveditem()

        self.kiwoom = Kiwoom()
        self.kiwoom.comm_connect()

        fname = "ongoing_list.txt"
        if not os.path.isfile(fname):
            f = open(fname, 'wt')
            f.close()

        # 선정 종목 리스트
        self.load_buy_sell_list()
        self.file_upload()

        self.timer = QTimer(self)
        self.timer.start(1000)
        self.timer.timeout.connect(self.timeout)

        #실시간 현재가
        self.scrnum = 5000
        self.set_current()
        self.kiwoom.OnReceiveRealData.connect(self.kiwoom._receive_real_data)
        self.kiwoom.sig_cl.sig_.connect(self.stockgridview)

        accouns_num = int(self.kiwoom.get_login_info("ACCOUNT_CNT"))
        accounts = self.kiwoom.get_login_info("ACCNO")
        accounts_list = accounts.split(';')[0:accouns_num]

        self.comboBox.addItems(accounts_list)
        self.exe_save = 0
        self.pushButton.clicked.connect(self.save_ongoing)
        #self.check_chejan_balance()
        self.check_balance()

        # 주문 들어가는 부분
        self.timer3 = QTimer(self)
        self.timer3.start(1000 * 10)
        self.timer3.timeout.connect(self.timeout3)

    # 화면번호
    def getnum(self):
        if self.scrnum < 9999:
            self.scrnum += 1
        else:
            self.scrnum = 5000
        return int(self.scrnum)

    #실시간 현재가 불러오기 위한 종목코드 수집
    def file_upload(self):
        # 오늘의 추천 파일만 확인
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        self.ncode = []
        #self.check_price = []
        for i in range(len(buy_list)):
            split_row_data = buy_list[i].split(' ')
            self.ncode.append(split_row_data[8])
            #self.check_price.append(split_row_data[14])

    #실시간 설정
    def set_current(self):
        print(self.ncode)
        for i in range(0, len(self.ncode)):
            self.kiwoom._set_real_reg(self.getnum(), self.ncode[i], "9001;10",
                                      "0")

    def stockgridview(self):
        item_cnt = len(self.saveditem.item_view)
        self.scode_list = list(self.saveditem.item_view.keys())
        self.tableWidget_5.setRowCount(item_cnt)
        for i in range(item_cnt):
            for j in range(3):
                #print(self.savedstockitem.item_view[self.scode_list[i]][j])
                item = QTableWidgetItem(
                    self.saveditem.item_view[self.scode_list[i]][j])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_5.setItem(i, j, item)

    # 버튼으로 파일 저장
    def save_ongoing(self):
        self.exe_save = 1
        self.check_chejan_balance()

    # 거래시간 확인
    def is_trading_time(self):
        global special
        vals = []
        current_time = datetime.datetime.now().time()
        #print(current_time)
        for start, end in TRADING_TIME:
            # 수능날
            now = datetime.datetime.now()
            soo_day = datetime.datetime.today().weekday()
            soo = now.isocalendar()
            # 수능날
            if soo_day == 3 and soo[1] == 46:
                start_time = datetime.time(hour=9, minute=start[1])
                end_time = datetime.time(hour=16, minute=end[1])
            # 새해 다음날
            elif now.month == 1 and now.day == 2:
                start_time = datetime.time(hour=9, minute=start[1])
                end_time = datetime.time(hour=end[0], minute=end[1])
            else:
                start_time = datetime.time(hour=start[0], minute=start[1])
                end_time = datetime.time(hour=end[0], minute=end[1])

            if (current_time >= start_time and current_time <= end_time):
                vals.append(True)
            else:
                vals.append(False)
                pass
        if vals.count(True):
            return True
        else:
            return False

    def is_end_time(self):
        vals = []
        current_time = datetime.datetime.now().time()
        for start, end in TRADING_TIME:
            now = datetime.datetime.now()
            soo_day = datetime.datetime.today().weekday()
            soo = now.isocalendar()
            # 수능날
            if now.month == 11 and soo_day == 3:
                if soo[1] == 46:
                    start_time = datetime.time(hour=16, minute=20)
            # 새해 다음날
            elif now.month == 1 and now.day == 2:
                start_time = datetime.time(hour=15, minute=20)
            # 동시 호가 시간 포함한 3시 30분
            else:
                end_che = datetime.time(hour=4, minute=15)
                start_time = datetime.time(hour=end[0], minute=end[1] + 10)
            if (current_time >= start_time):
                vals.append(True)
            elif (current_time >= end_che and current_time <= start_time):
                vals.append(False)
            else:
                vals.append(False)
                pass
        if vals.count(True):
            return True
        else:
            return False

    # 자동 주문
    def trade_stocks(self):
        self.is_order_correct()
        hoga_lookup = {'지정가': "00", '시장가': "03"}

        global lr_list
        global pr_list

        current_time = datetime.datetime.now()

        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        account = self.comboBox.currentText()

        now = datetime.datetime.now()
        soo_day = datetime.datetime.today().weekday()
        soo = now.isocalendar()
        today_hd = datetime.datetime.today().strftime("%Y%m%d")

        order_check1 = ["주문완료", "매도완료"]

        # 매수
        for i in range(len(buy_list)):
            split_row_data = buy_list[i].split(' ')
            machine = split_row_data[0]
            code = split_row_data[8]
            num = split_row_data[13]
            price = split_row_data[14]
            hoga = "지정가"

            #print("first_order", self.first_order)
            if self.is_trading_time() == True:
                if code in self.scode_list:
                    if not machine in order_check1:
                        if int(price) <= int(
                                self.saveditem.item_view[code][1]):
                            print("{0}: 코드, {1}: 주문가격 {2}: 현재가".format(
                                code, int(price),
                                int(self.saveditem.item_view[code][1])))
                            self.kiwoom.send_order("send_order_req", "0101",
                                                   account, 1, code, int(num),
                                                   int(price),
                                                   hoga_lookup[hoga], "")
                            buy_list[i] = buy_list[i].replace(
                                machine, order_check1[0])
            f = open("buy_list.txt", 'wt')
            for row_data in buy_list:
                f.write(row_data)
        # 매도
        num_data = len(self.kiwoom.opw00018_output['multi'])

        for i in range(num_data):
            code_name = self.kiwoom.opw00018_output['compare'][i][0]
            quantity = self.kiwoom.opw00018_output['compare'][i][1]
            current_price = self.kiwoom.opw00018_output['compare'][i][2]
            purchase_price = self.kiwoom.opw00018_output['compare'][i][3]
            print("종목이름: %s, 현재가격: %s, 구입가격: %s" %
                  (code_name, current_price, purchase_price))

            location = 0
            while (location < len(current_price)):
                if current_price[location] == ',':
                    current_price = current_price[:location] + current_price[
                        location + 1::]
                location += 1
            current_price = int(current_price)

            location2 = 0
            while (location2 < len(purchase_price)):
                if purchase_price[location2] == ',':
                    purchase_price = purchase_price[:
                                                    location2] + purchase_price[
                                                        location2 + 1::]
                location2 += 1

            for j in range(len(buy_list)):
                split_row_data = buy_list[j].split(' ')
                machine = split_row_data[0]
                hd = split_row_data[7]
                code = split_row_data[8]
                num = split_row_data[13]
                price = split_row_data[14]
                pr = split_row_data[15]
                lr = split_row_data[16].replace("\n", "")
                hoga = "지정가"

                code_new = self.kiwoom.get_master_code_name(code)

                due_time = current_time.replace(hour=15,
                                                minute=15,
                                                second=0,
                                                microsecond=0)
                if soo_day == 3 and soo[1] == 46:
                    due_time = current_time.replace(hour=16,
                                                    minute=15,
                                                    second=0,
                                                    microsecond=0)

                if due_time < current_time and machine == "주문완료":
                    print(hd, today_hd)
                    if hd == today_hd:
                        self.kiwoom.send_order("send_order_req", "0101",
                                               account, 2, code, num,
                                               current_price,
                                               hoga_lookup[hoga], "")
                        print("hd 만료, 시장가 판매")
                        buy_list[j] = buy_list[j].replace(machine, "매도완료")

                #if code_name == code_new and int(quantity) >= int(num): << 에러남 확인 바람
                if code_name == code_new:
                    print("code name: %s, lr: %f, pr: %f" %
                          (code, float(lr), float(pr)))
                    pr_price = float(pr) * int(purchase_price)
                    print("pr_price: %f * %d = %d" %
                          (float(pr), int(purchase_price), int(pr_price)))
                    lr_price = float(lr) * float(purchase_price)
                    pr_price = int(pr_price)
                    lr_price = int(lr_price)
                    lr_list[code_name] = lr_price
                    pr_list[code_name] = pr_price
                    print("profit rate price: ", pr_price)
                    print("loss rate price: ", lr_price)
                    print("current price: ", current_price)

                    if machine == "주문완료" and self.is_trading_time() == True:

                        if (current_price >= pr_price):
                            self.kiwoom.send_order("send_order_req", "0101",
                                                   account, 2, code, num,
                                                   current_price,
                                                   hoga_lookup[hoga], "")
                            print("pr 주문완료")
                            print(account, code, num, current_price,
                                  hoga_lookup[hoga])
                            buy_list[j] = buy_list[j].replace(machine, "매도완료")
                            break

                        elif current_price <= lr_price:
                            self.kiwoom.send_order("send_order_req", "0101",
                                                   account, 2, code, num,
                                                   current_price,
                                                   hoga_lookup[hoga], "")
                            print(account, code, num, current_price,
                                  hoga_lookup[hoga])
                            buy_list[j] = buy_list[j].replace(machine, "매도완료")
        print(lr_list)
        print(pr_list)

        # file update
        f = open("buy_list.txt", 'wt')
        for row_data in buy_list:
            f.write(row_data)
        f.close()

    def load_buy_sell_list(self):

        global file_changed

        current_time = datetime.datetime.now()
        today_file = datetime.datetime.today().strftime("%Y%m%d")

        file_name = today_file + "추천.txt"
        print(file_name)

        if os.path.isfile(file_name) == False:
            print("오늘의 추천 파일을 찾을 수 없습니다.")

        elif file_changed == False and current_time < current_time.replace(
                hour=15, minute=16):
            print(file_name, " buy_list로 변환")
            f = open(file_name, 'rt')
            temp_list = f.readlines()
            f.close()

            frow_data = []
            for row_data in temp_list:
                frow_data.append(' '.join(row_data.split()))
            frow_data = filter(str.strip, frow_data)
            temp = []
            for x in frow_data:
                temp.append(x)

            bl = []
            for j in range(2, len(temp) - 1):
                x = []
                split_row_data = temp[j].split(' ')
                split_row_data[7] = (
                    split_row_data[7][split_row_data[7].find("(") +
                                      1:split_row_data[7].find(")")])
                split_row_data[8] = re.sub(r'\([^)]*\)', '', split_row_data[8])
                split_row_data[9] = split_row_data[9].replace("원", "")
                split_row_data[9] = split_row_data[9].replace(",", "")
                split_row_data[13] = split_row_data[13].replace("주", "")
                split_row_data[13] = split_row_data[13].replace(",", "")
                split_row_data[14] = split_row_data[14].replace("원", "")
                split_row_data[14] = int(split_row_data[14].replace(",", ""))

                for i in range(len(split_row_data)):
                    x.append(split_row_data[i])
                x = map(str, x)
                y = " ".join(x)
                bl.append(y)

            # 전날 미매도 파일 불러오기
            f = open("ongoing_list.txt", 'rt')
            sell_list = f.readlines()
            sell_list2 = [s.rstrip() for s in sell_list]
            bl += sell_list2
            f.close()

            f = open("buy_list.txt", 'wt')
            for i in range(len(bl)):
                # print(bl[i])
                f.write(bl[i])
                f.write("\n")
            f.close()

            file_changed = True
            print("file_changed?? ", file_changed)

        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        row_count = len(buy_list)
        self.tableWidget_3.setRowCount(row_count)

        self.num_name = {}
        # buy list
        # j:행, i:열
        for j in range(len(buy_list)):
            split_row_data = buy_list[j].split(' ')
            temp_name = split_row_data[8]
            # 종목명 구하기
            code_name = self.kiwoom.get_master_code_name(temp_name)
            self.num_name[code_name] = temp_name

            for i in range(len(split_row_data)):
                item = QTableWidgetItem(split_row_data[i].rstrip())
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignCenter)
                self.tableWidget_3.setItem(j, i, item)

        self.tableWidget_3.resizeRowsToContents()
        print("num_name", self.num_name)

    def timeout(self):
        # market_start_time = QTime(9, 0, 0)
        current_time = QTime.currentTime()
        """if current_time > market_start_time and self.trade_stocks_done is False:
            self.trade_stocks()
            self.trade_stocks_done = True"""
        now = QDate.currentDate()
        text_time = now.toString(
            Qt.DefaultLocaleLongDate) + " " + current_time.toString("hh:mm:ss")
        time_msg = text_time

        state = self.kiwoom.get_connect_state()
        if state == 1:
            state_msg = "서버 연결 중"
        else:
            state_msg = "서버 미 연결 중"

        self.statusbar.showMessage(state_msg + " | " + time_msg)

    def timeout3(self):
        print(datetime.datetime.now())
        self.check_balance()
        print("check_balance 완료")
        self.check_chejan_balance()
        print("check_chejan_balance 완료")
        self.trade_stocks()
        print("trade_stocks 완료")
        self.load_buy_sell_list()
        print("load_buy_sell_list 완료")

    def check_chejan_balance(self):
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        name = []
        num_order = []
        file_price = []
        buy_list2 = []
        check_order = []
        self.first_order = {}

        for i in range(len(buy_list)):
            split_row_data = buy_list[i].split(' ')
            machine = split_row_data[0]
            code = split_row_data[8]
            num = split_row_data[13]
            price = int(split_row_data[14])
            name.append(code)
            num_order.append(num)
            file_price.append(price)
            check_order.append(machine)
        # SetInputValue(입력 데이터 설정)과 CommRqData(TR 요청)
        # 최대 20개의 보유 종목 데이터 리턴 반복
        self.kiwoom.reset_opt10075_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opt10075_req", "opt10075", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opt10075_req", "opt10075", 0, "2000")
            # if self.is_trading_time() == False:
            #    break

        item_count = len(self.kiwoom.opt10075_output['no_che'])
        self.tableWidget_4.setRowCount(item_count)

        for j in range(item_count):
            row = self.kiwoom.opt10075_output['no_che'][j]
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_4.setItem(j, i, item)
                # 매수만 된 종목 확인
                if row[0] == '접수':
                    if row[1] == '+매수':
                        self.first_order[int(self.num_name[self.kiwoom.opt10075_output['no_che'][j][3]])] = \
                        int(self.kiwoom.opt10075_output['no_che'][j][7])
                # ongoin_list 저장
                if self.is_end_time() == True or self.exe_save == 1:
                    if row[0] == '체결':
                        # 오늘자 파일의 매수 확인 후 ongoing_list에 저장
                        if row[1] == '+매수':
                            # if row[1] == '-매도':
                            for l in range(0, j + 1):
                                if self.kiwoom.opt10075_output['no_che'][l][3] == \
                                        self.kiwoom.opt10075_output['no_che'][j][3]:
                                    # print("l-{0} {1}".format(l, self.kiwoom.opt10075_output['no_che'][l]))
                                    # print("j-{0} {1}".format(j, self.kiwoom.opt10075_output['no_che'][j]))
                                    # 후에 매도가 됐는지 확인
                                    if not self.kiwoom.opt10075_output[
                                            'no_che'][l][1] == '-매도':
                                        for k in range(len(buy_list)):
                                            if int(self.num_name[self.kiwoom.opt10075_output['no_che'][j][3]]) == int(name[k]) \
                                                    and int(self.kiwoom.opt10075_output['no_che'][j][4]) == int(num_order[k])\
                                                    and int(self.kiwoom.opt10075_output['no_che'][j][7]) == int(file_price[k]):
                                                #print(buy_list[k])
                                                #buy_list[k].replace(self.check_price[k], '-1')
                                                buy_list2.append(buy_list[k])
                        # 계속 감시 중인 종목이 매도되지 않을 시 ongoing_list에 추가
                        elif row[1] == '-매도':
                            for s in range(len(buy_list)):
                                if check_order[s] == "주문완료":
                                    if not int(self.num_name[self.kiwoom.opt10075_output['no_che'][j][3]]) == int(name[s]) \
                                        and int(self.kiwoom.opt10075_output['no_che'][j][4]) == int(num_order[s]):
                                        buy_list2.append(buy_list[s])

                                # print(self.kiwoom.opt10075_output['no_che'][j][3])
                                # print("l - %d, j - %d" %(l, j))
                                # print("확인용", self.kiwoom.opt10075_output['no_che'][l])
                            """for k in range(len(buy_list)):
                                if int(self.num_name[row[3]]) == int(name[k]):
                                    #print(k)
                                    #print(buy_list[k])
                                    buy_list2.append(buy_list[k])"""
        buy_list2 = list(set(buy_list2))
        if self.is_end_time() == True or self.exe_save == 1:
            f = open("ongoing_list.txt", 'wt')
            for row_data in buy_list2:
                row_data = row_data
                f.write(row_data)
            f.close()

        self.exe_save = 0
        self.tableWidget_4.resizeRowsToContents()

    # 잔고 및 보유 계좌 정보 확인
    def check_balance(self):
        self.kiwoom.reset_opw00018_output()
        account_number = self.kiwoom.get_login_info("ACCNO")
        account_number = account_number.split(';')[0]

        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 0, "2000")

        while self.kiwoom.remained_data:
            time.sleep(0.2)
            self.kiwoom.set_input_value("계좌번호", account_number)
            self.kiwoom.comm_rq_data("opw00018_req", "opw00018", 2, "2000")
        # opw00001
        # 예수금 데이터 얻어오기
        self.kiwoom.set_input_value("계좌번호", account_number)
        self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")
        #모의투자 시 밑의 세줄 주석 처리
        #self.kiwoom.set_input_value("비밀번호", "0000")
        #self.kiwoom.set_input_value("비밀번호입력매체구분", "00")
        #self.kiwoom.set_input_value("조회구분", 1)
        #self.kiwoom.comm_rq_data("opw00001_req", "opw00001", 0, "2000")
        # balance
        # 예수금 데이터 tableWidget에 출력
        item = QTableWidgetItem(self.kiwoom.d2_deposit)
        item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
        self.tableWidget.setItem(0, 0, item)

        # 해당 칼럼에 값 추가
        for i in range(1, 6):
            print(self.kiwoom.opw00018_output['single'][i - 1])
            item = QTableWidgetItem(self.kiwoom.opw00018_output['single'][i -
                                                                          1])
            item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
            self.tableWidget.setItem(0, i, item)
        # 아이템 크기에 맞춰 행 높이 조절
        self.tableWidget.resizeRowsToContents()
        # Item list 보유종목 출력
        item_count = len(self.kiwoom.opw00018_output['multi'])
        self.tableWidget_2.setRowCount(item_count)
        for j in range(item_count):
            row = self.kiwoom.opw00018_output['multi'][j]
            if row[0] in lr_list and pr_list:
                str_lr = str(lr_list[row[0]])
                row[4] = str_lr
                print(row[4])
                str_pr = str(pr_list[row[0]])
                row[5] = str_pr
                print(row[5])
            print(row)
            for i in range(len(row)):
                item = QTableWidgetItem(row[i])
                item.setTextAlignment(Qt.AlignVCenter | Qt.AlignRight)
                self.tableWidget_2.setItem(j, i, item)
        self.tableWidget_2.resizeRowsToContents()

    # 매수 조건은 완료하였지만 실제 매수가 안 되는 경우가 있어 확인
    def is_order_correct(self):
        f = open("buy_list.txt", 'rt')
        buy_list = f.readlines()
        f.close()

        order_check1 = ["주문완료", "매도완료"]

        # 매수
        for i in range(len(buy_list)):
            split_row_data = buy_list[i].split(' ')
            machine = split_row_data[0]
            code = split_row_data[8]
            num = split_row_data[13]
            price = split_row_data[14]
            hoga = "지정가"

            if machine == order_check1[0]:
                if not int(code) in self.first_order:
                    buy_list[i] = buy_list[i].replace(machine, "미매수")

                f = open("buy_list.txt", 'wt')
                for row_data in buy_list:
                    f.write(row_data)