퀀트투자

한국투자증권 OpenAPI 사용하기(1) - mojito

Like_Me 2023. 11. 4. 15:04
반응형

자동 매매 프로그램을 만들기 위해 다양한 증권사의 API를 사용한 적이 있습니다. 키움, 대신, 이베스트 등을 사용했었는데, 사용하기 쉬운 느낌은 아니었습니다. 사용해 본 적도 없는 PyQT나 이벤트 처리 등을 하는 게 낯설어 처음엔 좀 헤매기도 했습니다. 그런데 드디어 한국투자증권이 Rest API 기반의 오픈 API 서비스를 제공하기 시작했습니다. 이를 모히토(mojito) ([1])라는 라이브러리로 사용하기 쉽게 만들어 주신 고마운 분도 계십니다. 이 라이브러리를 사용하면 파이썬 기초만 아시는 분들도 자동 매매 프로그램을 만들 수 있을 정도로 좋아 보여 이를 활용해서 퀀트 투자를 할 수 있는 방법에 대해 알아보겠습니다.

 

당연히 한투증권의 api를 사용하기 위해서는 계좌 개설 및 open api를 사용하기 위한 key와 secret key를 알아야 합니다. 이에 대한 방법은 [1]에 이미 잘 나와 있어 생략하고 삼성전자를 매수하는 방법을 알아보겠습니다.

 

우선 필요한 라이브러리들을 불러오고 미리 저장해둔 key, secret, 계좌번호를 모두 불러옵니다. 한투 api와 연결하기 위해 mojito를 사용해 broker 인스턴스를 생성해 줍니다.

import mojito
import yaml

print(mojito.__version__)

with open("data/koreainvestment.yaml") as f:
    info_data = yaml.load(f, Loader=yaml.FullLoader)

key = info_data['key']
secret = info_data['secret']
acc_no = info_data['acc_no']

broker = mojito.KoreaInvestment(
    api_key=key,
    api_secret=secret,
    acc_no=acc_no
)

이후 현재 계좌에 대한 정보를 불러오겠습니다.

# NOTE 잔고 조회
balance_info = broker.fetch_balance()

for comp in balance_info['output1']:
    print(comp['pdno'])  # 종목코드
    print(comp['prdt_name'])  # 종목명
    print(comp['hldg_qty'])  # 보유수량
    print(comp['ord_psbl_qty'])  # 주문 가능 수량
    print(comp['pchs_amt'])  # 매입금액
    print(comp['evlu_amt'])  # 평가금액
    print("-" * 40)

# 총 평가금액
tot_evlu_amt = balance_info['output2']['tot_evlu_amt']
# 예수금
dnca_tot_amt = balance_info['output2']['dnca_tot_amt']
# 금일 매수 금액
thdt_buy_amt = balance_info['output2']['thdt_buy_amt']

위에서 내가 가진 종목에 대한 정보(output1)와 계좌에 대한 정보(output2)를 볼 수 있습니다. output2에서 불러온 예수금에 대한 정보와 현재 삼성전자 가격을 사용해서 매수 주문을 넣어보겠습니다.

 

# NOTE 현재가 조회 (장 종료 후에는 종가)
prpr = broker.fetch_price("005930")
print(prpr['rt_cd'])  # 0이면 성공 아니면 실패
print("Open:  ", prpr['output']['stck_oprc'])   # 시가
print("High : ", prpr['output']['stck_hgpr'])    # 고가
print("Low  : ", prpr['output']['stck_lwpr'])     # 저가
print("Close: ", prpr['output']['stck_prpr'])    # 종가


want_buy_price = prpr['output']['stck_prpr'] # 종가를 기준으로 매수
want_buy_quantity = dnca_tot_amt//want_buy_price
# NOTE 지정가 매수
maesu = broker.create_limit_buy_order(
    symbol="005930",  # 삼성전자 코드
    price=want_buy_price,  # 지정가 매수시 가격단위를 고려해야 함.
    quantity=want_buy_quantity
)
if maesu['rt_cd'] == '0':
    print("삼성전자 매수 주문 성공.")
else:
    print("삼성전자 매수 주문 실패.")
    
'''
예시 output, NOTE 영업점커드와 주문번호는 주문 취소시 필요하다!
{'msg1': '주문 전송 완료 되었습니다.',
 'msg_cd': 'APBK0013',
 'output': {'KRX_FWDG_ORD_ORGNO': '91252', # 영업점코드
            'ODNO': '0000026614', # 주문번호
            'ORD_TMD': '090312'}, # 주문시각(시분초HHMMSS)
 'rt_cd': '0'} # rt_cd로 성공체크.
'''

삼성전자를 현재가격(종가) 기준으로 예수금의 전부를 사용해서 매수하는 코드를 작성했습니다. api를 사용할 때 주의할 점 중에 하나가 주문 혹은 조회가 실패할 수 있는 경우가 있다는 것입니다. 현재는 실패했을 때 print만 하도록 처리했지만 실제 거래를 할 때는 따로 처리해야 합니다. 성공할 때까지 하던지 아니면 넘기던지 다양한 경우를 생각해 볼 수 있을 것입니다.

코드 아래에 maesu 가 리턴받는 예시도 작성해 놨는데, 영업점 코드, 주문 번호는 추후 필요할 수 있으니 여러 종목을 주문하고자 할 때는 반드시 따로 저장해 둬야 합니다. 주문 취소는 아래와 같은 방법을 쓰면 됩니다.

# NOTE 주문 취소
resp = broker.cancel_order(
    org_no=maesu['output']['KRX_FWDG_ORD_ORGNO'],
    order_no=maesu['output']['ODNO'],
    quantity=want_buy_quantity,  # 잔량전부 취소시 원주문 수량과 일치해야함
    total=True   # 잔량전부를 의미
)

주문 취소도 전량을 하는 방법과 그렇지 않은 방법이 있는데 여기서는 전량을 취소하는 방법에 대한 코드입니다. 위에서 매수 주문을 하고 얻은 영업점 코드와 주문 번호를 가지고 취소를 해야 함을 볼 수 있습니다. 

 

간단한 예시를 알아봤는데, 모히토 라이브러리를 사용하다 보니 확실히 사용하기 쉽고 편하다는 강력한 장점이 느껴졌습니다. 다만 아쉬운 점은 다른 증권사 api에 비해 가격 데이터를 불러오는 것(실시간+과거 모두)이 훨씬 느리더군요. 하지만 단기 트레이딩을 위한 툴을 만드려고 하는 것이 아니라면 충분해 보이고, 특히 퀀트 투자를 하고자 하는 분들이 사용하기 적합해 보입니다. 

 

 

Ref[1] https://wikidocs.net/165190

 

01) 모히토 모듈

[TOC] ## 모히토 (Mojito) 모듈 2022년 드디어 국내 증권사 최초로 한국투자증권이 Rest API 기반의 오픈API 서비스를 제공하기 시작했습니다. 이제 누구…

wikidocs.net

 

반응형