PyInstaller exe 백신 오탐 — 자동매매 확인 5단계
파이썬 자동매매 봇을 PyInstaller로 묶은 exe가 "Windows의 PC 보호" 창이나 백신 경고에 걸리는 것은 대부분 오탐이지만, '대부분'이라서 확인 없이 실행하면 안 됩니다. 먼저 경고가 SmartScreen(평판 부족 — 실행 버튼이 있음)인지, Defender 실시간 보호(파일 격리 — 탐지명이 있음)인지 구분하고, ① 제작사가 알려 준 SHA-256 해시와 Get-FileHash 결과를 대조 ② 서명 확인 ③ 다운로드 출처 확인 ④ VirusTotal은 업로드 말고 해시로 검색 ⑤ 탐지명 확인 순서로 봅니다. 예외 등록은 봇 폴더 하나만 좁게 걸고, KIS·키움 appkey/appsecret는 exe 안에 넣지 말고 별도 설정 파일로 분리해야 합니다.
목차
- 경고 창 3종 — 무엇이 막았는지부터
- 봇 exe가 유독 잘 걸리는 이유
- 실행 전 확인 5단계 (PowerShell 실물)
- VirusTotal에 올리기 전에 — 키가 박힌 exe
- 예외 등록은 폴더 하나만
- 제작사가 해야 할 일
- 의뢰 단계에서 미리 정할 것
- 자주 묻는 질문
상황은 대개 이렇습니다. 제작을 맡긴 자동매매 프로그램 AlgoBot.exe를 받아 더블클릭했더니 파란 창이 뜹니다. "Windows의 PC 보호 — Microsoft Defender SmartScreen에서 인식할 수 없는 앱의 시작을 차단했습니다." 혹은 아무 창도 없이 파일이 사라지고, 알림 센터에 "위협이 발견됨"이 남습니다. 장 시작 30분 전이면 판단이 급해집니다. 이 글은 그 순간에 무엇을 확인하고, 무엇은 하면 안 되는지를 순서대로 정리합니다. 개발을 몰라도 PowerShell 창에 복사해 붙이면 되는 명령만 씁니다.
1. 경고 창 3종 — 무엇이 막았는지부터
"백신에 걸렸다"는 말 안에 성격이 전혀 다른 세 가지가 섞여 있습니다. 대처가 다르니 먼저 구분합니다.
| 무엇 | 보이는 모습 | 의미 | 사용자가 할 수 있는 것 |
|---|---|---|---|
| SmartScreen | 파란 창 "Windows의 PC 보호" · 추가 정보 → 실행 | 악성이라는 판정이 아니라 평판이 아직 없다는 뜻 | 출처·해시 확인 후 실행 |
| Defender 실시간 보호 | 파일이 사라짐 · "위협이 발견됨" · 탐지명 표시 | 파일 내용이나 행동이 패턴에 걸림(오탐 가능) | 탐지명 확인 → 제작사 문의 → 필요 시 복원 |
| 스마트 앱 컨트롤(Windows 11) | 실행 버튼이 없는 차단 | 서명 없는 앱을 평판이 없으면 차단 | 개별 허용 불가 — 서명된 빌드 요청 |
Microsoft 공식 문서(SmartScreen reputation for Windows app developers)는 서명이 없는 파일에 대해 "Windows protected your PC" 경고가 뜨고 사용자가 Run anyway를 골라야 실행된다고 적고 있습니다. 같은 문서는 스마트 앱 컨트롤이 SmartScreen보다 우선할 수 있으며 평판 없는 미서명 파일을 실행 자체를 막는다고 설명하고, Microsoft 지원 FAQ는 스마트 앱 컨트롤에 앱별 예외를 두는 방법이 현재는 없다고 밝힙니다. 그래서 스마트 앱 컨트롤이 켜진 PC에서는 "추가 정보 → 실행"이 아예 보이지 않습니다. 이 경우 기능 전체를 끄는 것보다 제작사에 서명된 빌드를 요청하는 편이 맞습니다.
2. 봇 exe가 유독 잘 걸리는 이유
같은 파이썬 프로그램이라도 자동매매 봇은 백신이 의심하는 조건을 여러 개 동시에 갖춥니다. 프로그램이 나빠서가 아니라 만드는 방식과 하는 일 때문입니다.
만드는 방식 — 서명 없음 + 매 빌드 새 해시
- PyInstaller 부트로더를 수많은 프로그램이 공유합니다. 악성 프로그램도 같은 도구로 만들어지기 때문에, 부트로더 부분만 보고 의심하는 탐지가 생깁니다. 커뮤니티에서 흔히 보고되는 Defender 탐지명이
Trojan:Win32/Wacatac계열(끝에!ml이 붙으면 기계학습 판정)입니다. --onefile빌드는 실행할 때마다%TEMP%\_MEIxxxxxx폴더에 압축을 풀고 그 안의 파이썬 런타임을 띄웁니다. "임시 폴더에 실행 파일을 풀어 실행"은 백신이 싫어하는 행동입니다.- SmartScreen 평판은 파일 해시 단위로 쌓입니다. Microsoft 문서는 서명이 없으면 새 버전마다 평판이 0에서 다시 시작한다고 적고 있습니다. 맞춤 제작 봇은 고객 1명에게 1개 빌드가 가니 다운로드 수가 쌓일 수 없습니다 — 사실상 항상 첫 실행입니다.
하는 일 — 봇의 정상 동작이 의심 행동과 닮았다
| 봇이 하는 일 | 실제 예 | 백신 눈에는 |
|---|---|---|
| 외부 서버와 상시 HTTPS·WebSocket 통신 | KIS openapi.koreainvestment.com:9443(모의 openapivts) · 키움 REST API api.kiwoom.com(모의 mockapi.kiwoom.com) · 업비트 api.upbit.com · Binance api.binance.com | 원격 서버와 지속 연결 |
| 키 입력·창 조작 자동화 | 키움 OpenAPI+ 자동 로그인(로그인 창에 비밀번호 입력) | 키로거·매크로와 비슷 |
| 시작 프로그램·작업 스케줄러 등록 | 재부팅 후 자동 기동 | 지속성 확보 |
| 토큰·로그 파일 반복 쓰기 | KIS access_token 캐시, 체결 로그 | 파일 다량 생성 |
| COM/OCX 로드 | 키움 OpenAPI+ KHOpenAPI 컨트롤(32비트) | 시스템 구성요소 호출 |
특히 키움 OpenAPI+ 기반 봇은 32비트 파이썬으로 빌드해야 하고 로그인 창 자동화가 붙는 경우가 많아 오탐 빈도가 높은 편입니다. 무인 로그인 구성은 키움 OpenAPI 자동 로그인 무인 운영에, 설치 단계 오류는 키움 OpenAPI 설치 문제 해결에 따로 정리했습니다. REST 방식(키움 REST API·KIS)은 창 자동화가 없어 이 항목이 빠지지만, 서명·해시 문제는 똑같이 남습니다.
3. 실행 전 확인 5단계 (PowerShell 실물)
시작 메뉴에서 Windows PowerShell을 열고 아래를 차례로 붙여 넣습니다. 경로 C:\AlgoBot\AlgoBot.exe는 본인 위치로 바꾸십시오.
① 해시 대조 — 받은 파일이 제작사가 만든 그 파일인가
Get-FileHash C:\AlgoBot\AlgoBot.exe -Algorithm SHA256
Algorithm Hash Path
--------- ---- ----
SHA256 3F1C9A...(64자리)...E07B C:\AlgoBot\AlgoBot.exe
제작사가 메신저·메일로 따로 알려 준 SHA-256 값과 64자리가 전부 같아야 합니다. 한 글자라도 다르면 전송 중 손상됐거나 다른 파일입니다 — 실행하지 말고 다시 받으십시오. 이 단계가 가장 중요합니다. 백신 판정은 확률이지만 해시 일치는 "제작사가 넘긴 바로 그 파일"이라는 사실 확인이기 때문입니다. 해시를 따로 알려 주지 않는 제작사라면 요청하십시오.
② 서명 확인
Get-AuthenticodeSignature C:\AlgoBot\AlgoBot.exe | Format-List Status, SignerCertificate
Status : NotSigned
SignerCertificate :
개인·소규모 제작 봇은 NotSigned가 대부분이고, 그 자체로 위험 신호는 아닙니다. 서명된 파일이면 Valid와 함께 인증서 주체(회사명)가 나오는데, 그 이름이 계약한 제작사와 같은지 보십시오. HashMismatch가 나오면 서명 후 파일이 바뀐 것이니 실행하지 않습니다.
③ 다운로드 출처 표시(Mark of the Web)
Get-Content C:\AlgoBot\AlgoBot.exe -Stream Zone.Identifier
[ZoneTransfer]
ZoneId=3
HostUrl=https://...
ZoneId=3은 인터넷에서 받은 파일이라는 표시이고, SmartScreen이 검사하는 계기가 됩니다. HostUrl이 제작사가 안내한 주소(드라이브 공유 링크 등)와 같은지 확인합니다. ①②③이 모두 맞으면 SmartScreen 창의 추가 정보 → 실행을 눌러도 됩니다. 파일 속성의 차단 해제나 Unblock-File도 같은 효과지만, 확인을 마친 뒤에만 쓰십시오.
④ VirusTotal — 업로드 말고 해시로 검색
VirusTotal 검색창에 ①의 해시 64자리를 붙여 넣습니다. 이미 누군가 올린 적이 있으면 결과가 나오고, 처음 보는 파일이면 "찾을 수 없음"이 나옵니다. 맞춤 제작 봇은 보통 후자입니다. 여기서 파일을 바로 올리지 않는 이유는 4장에서 설명합니다.
⑤ 탐지명 확인 — 격리됐다면
Get-MpThreatDetection | Select-Object InitialDetectionTime, ThreatID, Resources
Get-MpThreat | Select-Object ThreatID, ThreatName, SeverityID
두 결과를 ThreatID로 맞춰 보면 어떤 파일이 어떤 이름으로 잡혔는지 나옵니다. 화면으로 보려면 Windows 보안 → 바이러스 및 위협 방지 → 보호 기록입니다. 이 탐지명을 그대로 제작사에 보내십시오. "백신에 걸려요"보다 탐지명 + 해시가 훨씬 빨리 해결됩니다. 탐지명이 Wacatac·!ml 같은 일반·기계학습 판정이면 오탐일 가능성이 높고, 특정 악성코드 계열명(정보 탈취형 등)이면 실행하지 말고 제작사 확인을 먼저 받습니다.
하지 말 것 — 경고가 귀찮다고 Defender 실시간 보호를 통째로 끄거나, 스마트 앱 컨트롤을 끈 채 그대로 두는 것. 봇 PC에는 증권사 계좌에 주문을 넣을 수 있는 키가 들어 있습니다. 백신을 끈 상태에서 다른 프로그램이 같은 PC에 들어오면 그 키가 그대로 노출됩니다.
4. VirusTotal에 올리기 전에 — 키가 박힌 exe
VirusTotal에 업로드한 파일은 이용 약관상 보안 업계(유료 이용자 포함)와 공유될 수 있습니다(최신 약관 확인). 여기에 자동매매 exe 특유의 문제가 겹칩니다. PyInstaller exe는 암호화된 상자가 아닙니다. pyinstxtractor 같은 공개 도구로 안의 .pyc를 꺼낼 수 있고, 코드에 문자열로 적어 둔 값은 그대로 읽힙니다.
# 이렇게 만든 exe라면 업로드 = 키 공개
APPKEY = "PSxxxxxxxxxxxxxxxxxxxx" # KIS appkey
APPSECRET = "xxxxxxxxxxxxxxxxxxxx..." # KIS appsecret
UPBIT_ACCESS = "xxxxxxxxxxxxxxxxxxxx" # 업비트 access key
KIS appkey/appsecret, 키움 REST API appkey/secretkey, 업비트·Binance API 키는 주문 권한이 있는 열쇠입니다. 그래서 키는 exe 바깥 파일로 두는 것이 정석입니다.
import json, os, sys
from pathlib import Path
BASE = Path(sys.executable).parent if getattr(sys, "frozen", False) else Path(__file__).parent
cfg = json.loads((BASE / "config.json").read_text(encoding="utf-8")) # exe 옆 파일, exe 안에 없음
APPKEY = cfg["kis"]["appkey"]
APPSECRET = cfg["kis"]["appsecret"]
# 또는 환경변수: os.environ["KIS_APPKEY"]
sys.frozen 분기는 PyInstaller로 묶였을 때 exe가 있는 폴더를, 개발 중에는 소스 폴더를 기준으로 삼게 하는 관용 코드입니다. 이렇게 만든 exe라면 키 없이 업로드해도 상대적으로 안전하지만, 그래도 해시 검색이 먼저입니다. 키 관리 전반(IP 제한·권한 최소화·유출 시 재발급)은 자동매매 API 키 보안 — 계좌를 지키는 설정에서 다뤘습니다.
5. 예외 등록은 폴더 하나만
확인을 마친 봇이 매번 격리된다면 Defender 예외를 겁니다. 범위는 봇 전용 폴더 하나로 좁힙니다. 관리자 권한 PowerShell에서:
Add-MpPreference -ExclusionPath "C:\AlgoBot"
Get-MpPreference | Select-Object -ExpandProperty ExclusionPath # 등록 확인
Remove-MpPreference -ExclusionPath "C:\AlgoBot" # 되돌리기
- 다운로드 폴더·바탕화면 전체를 예외로 걸지 않습니다. 이후 받는 모든 파일이 검사 없이 통과합니다.
--onefile빌드는%TEMP%\_MEI...에서 실행되므로 폴더 예외만으로는 계속 걸릴 수 있습니다. 이때 TEMP 전체를 예외로 걸지 말고, 제작사에--onedir(폴더형) 빌드를 요청하는 편이 낫습니다. 폴더형이 오탐을 반드시 줄인다는 보장은 없지만, 실행 위치가 예외 폴더 안에 고정됩니다.- V3 등 다른 백신을 쓰면 그 제품의 예외 설정과 오진 신고 창구를 이용합니다(각 제조사 공식 안내 확인).
예외를 건 뒤에는 그 폴더에 다른 프로그램을 넣지 않습니다. 봇을 VPS에서 돌린다면 같은 원칙을 서버에도 적용하고, 재부팅·업데이트 대응은 윈도우 업데이트 재부팅, 봇 지키는 설정 5가지와 VPS 24시간 봇 운영 가이드를 함께 보십시오.
6. 제작사가 해야 할 일
오탐은 사용자가 아니라 만든 쪽이 줄이는 문제입니다. 납품하는 쪽이 할 수 있는 것은 다음과 같습니다.
| 조치 | 효과 | 공식 근거·주의 |
|---|---|---|
| 코드 서명 | 게시자 이름 표시, 같은 인증서로 평판 누적 | Microsoft 문서: EV 인증서도 더 이상 SmartScreen을 바로 통과시키지 않음(공식 문서 명시). Microsoft Artifact Signing(구 Trusted Signing)은 월 9.99달러부터라고 안내(가격 변동 가능) |
| 빌드마다 SHA-256 공지 | 사용자가 1단계를 할 수 있게 됨 | 비용 0 — 가장 먼저 할 것 |
| Microsoft에 오진 제출 | Defender 탐지 해제 | Microsoft Security Intelligence 파일 제출 포털(microsoft.com/wdsi/filesubmission) |
| PyInstaller 최신 버전·불필요 import 정리 | 탐지 요인 감소 | 효과는 버전·백신마다 다름 |
| 폴더형 빌드 또는 소스+가상환경 납품 | 임시 폴더 실행 회피 / exe 자체를 없앰 | 고객 PC에 파이썬 설치가 필요해질 수 있음 |
Microsoft 문서는 또 소비자용 SmartScreen 평판은 수동으로 심사를 신청하는 절차가 없고 다운로드가 쌓이며 자연히 생긴다고 적습니다. 즉 1인용 맞춤 봇은 서명을 해도 첫 실행 경고가 남을 수 있습니다. 이 사실을 납품 안내문에 미리 적어 두는 것이 문의를 가장 많이 줄입니다.
7. 의뢰 단계에서 미리 정할 것
견적을 받을 때 아래 다섯 줄을 물어보면, 납품 당일 백신 때문에 장을 놓치는 일을 줄일 수 있습니다.
- 납품 형태 — 단일 exe인가, 폴더형인가, 소스 코드인가. 소스 소유권 문제는 소스코드 소유권·에스크로 가이드 참고.
- 해시 공지 — 빌드마다 SHA-256을 따로 알려 주는가.
- 키 저장 방식 — KIS·키움 키가 exe 안에 들어가는가, 설정 파일로 분리되는가.
- 예외 등록 안내 — 어떤 폴더를 예외로 걸어야 하는지 문서로 주는가.
- 재빌드 대응 — 백신 업데이트로 갑자기 격리될 때 재빌드·오진 제출을 해 주는가.
이 항목들은 자동매매 외주 체크리스트 27개의 '납품·운영' 부분을 백신 관점에서 좁힌 것입니다. 완성품을 사는 경우라면 판매용 자동매매 프로그램 구매 전 확인도 함께 보십시오 — 출처를 확인할 수 없는 exe는 해시를 대조할 기준 자체가 없습니다.
이 글은 오탐 여부를 판단하는 절차를 안내할 뿐, 특정 파일이 안전하다고 보증하지 않습니다. 탐지명이 구체적인 악성 계열이거나 해시가 맞지 않으면 실행하지 마십시오. Windows·Defender 동작과 Microsoft 정책은 바뀔 수 있으니 공식 문서를 확인하십시오(2026-10-08 기준).
8. 자주 묻는 질문
자동매매 프로그램 exe가 백신에 걸리면 바이러스인가요?
대부분은 오탐이지만 확인 없이 단정할 수는 없습니다. PyInstaller로 묶은 파이썬 exe는 서명이 없고 빌드마다 해시가 새로워 SmartScreen 평판이 0이며, 외부 서버 상시 통신·자동 로그인 같은 봇의 정상 동작이 의심 행동과 닮아 탐지되기 쉽습니다. 제작사가 알려 준 SHA-256 해시와 Get-FileHash 결과가 일치하고 탐지명이 Wacatac·!ml 같은 일반 판정이면 오탐 가능성이 높습니다.
Windows의 PC 보호 창에서 실행을 눌러도 되나요?
해시 대조, 서명 확인, 다운로드 출처(Zone.Identifier의 HostUrl) 확인을 마친 뒤라면 추가 정보 → 실행을 눌러도 됩니다. 이 창은 악성 판정이 아니라 평판이 아직 없다는 SmartScreen 경고입니다. 스마트 앱 컨트롤이 켜진 Windows 11에서는 실행 버튼이 없으며, Microsoft는 앱별 예외 방법이 현재 없다고 안내합니다.
VirusTotal에 exe를 올려서 검사하면 안 되나요?
먼저 해시로 검색하십시오. 업로드한 파일은 약관상 보안 업계와 공유될 수 있고, PyInstaller exe는 pyinstxtractor 같은 도구로 내부 코드를 꺼낼 수 있어 KIS appkey·appsecret 같은 키가 코드에 들어 있으면 함께 노출됩니다. 키를 별도 설정 파일로 분리한 빌드인지 확인한 뒤에 업로드를 고려하십시오.
Defender 예외는 어떻게 거는 게 안전한가요?
봇 전용 폴더 하나만 Add-MpPreference -ExclusionPath로 등록하고, 다운로드 폴더나 TEMP 전체는 예외로 걸지 않습니다. 실시간 보호를 통째로 끄는 것은 피해야 합니다. --onefile 빌드는 임시 폴더에서 실행되므로 폴더 예외로 해결되지 않으면 제작사에 폴더형(--onedir) 빌드를 요청하는 편이 낫습니다.