Java XChange로 BitMEX WebSocket 인증 서명 만들기 (SignatureUtil + wss 예제)
암호화폐 마진 거래소인 BitMEX는 REST API뿐 아니라 WebSocket(wss) 인터페이스를 통해 실시간 시세, 주문 정보 등을 제공합니다. 이때, 개인 계정 정보나 주문 정보를 사용하려면 WebSocket 인증(authKeyExpires)을 통과해야 합니다.
이 글에서는 Java + XChange 라이브러리를 사용하여
authKeyExpires에 필요한 signature를 생성하는 방법과
직접 구현한 SignatureUtil 클래스를 정리합니다.
- BitMEX WebSocket 인증(authKeyExpires) 개념
- XChange의
BitmexDigest와ExpirationTimeFactory활용 SignatureUtil구현 코드ws.sendText로 실제 WebSocket 인증 요청 보내기
1. BitMEX WebSocket 인증(authKeyExpires)란?
BitMEX WebSocket에서 개인 데이터(포지션, 주문 등)에 접근하려면
authKeyExpires 메시지를 한 번 보내서 인증을 받아야 합니다.
요청 포맷은 다음과 같은 JSON 형태입니다.
{
"op": "authKeyExpires",
"args": [
"API_KEY",
EXPIRES,
"SIGNATURE"
]
}
- API_KEY : BitMEX에서 발급받은 API 키
- EXPIRES : 만료 시간(Unix timestamp 등, BitMEX 규격에 맞게 설정)
- SIGNATURE :
VERB + ENDPOINT + EXPIRES를 HMAC 서명한 값
이 글에서 소개하는 SignatureUtil 클래스는 바로 이
EXPIRES와 SIGNATURE 값을 생성하는 용도로 사용됩니다.
2. XChange 라이브러리 활용 포인트
Java에서 BitMEX에 연동할 때 많이 사용하는 라이브러리가 XChange (org.knowm.xchange) 입니다.
BitmexDigest: BitMEX 서명(HMAC) 생성을 도와주는 유틸ExpirationTimeFactory: 일정 시간 후 만료되는 nonce/타임스탬프 생성SynchronizedValueFactory<Long>: 스레드 안전한 증가 값 생성기 인터페이스
아래 예제에서는 BitmexDigest + ExpirationTimeFactory를 조합해서 WebSocket 서명에 필요한 EXPIRES와 signature를 만들어냅니다.
3. SignatureUtil 구현 (Java 코드)
먼저, BitMEX WebSocket 서명을 위한 SignatureUtil 클래스를 정리한 코드입니다.
import java.io.UnsupportedEncodingException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import org.knowm.xchange.bitmex.service.BitmexDigest;
import org.knowm.xchange.utils.nonce.ExpirationTimeFactory;
import si.mazi.rescu.SynchronizedValueFactory;
public class SignatureUtil {
// 30초 뒤 만료되는 타임스탬프(또는 nonce)를 생성하는 팩토리
private SynchronizedValueFactory<Long> nonceFactory = new ExpirationTimeFactory(30);
private Long EXPIRES = 0L;
private String API_SECRET;
private String API_KEY;
public SignatureUtil(String API_KEY, String API_SECRET) {
this.API_SECRET = API_SECRET;
this.API_KEY = API_KEY;
}
/**
* BitMEX WebSocket용 signature 생성 메서드
* VERB + ENDPOINT + EXPIRES 문자열을 HMAC 서명해서 반환
*/
public String bitmex_signature() throws UnsupportedEncodingException,
NoSuchAlgorithmException,
InvalidKeyException {
BitmexDigest BD = BitmexDigest.createInstance(API_SECRET);
String ENDPOINT = "/realtime";
String VERB = "GET";
String BITMEX_URL = "wss://www.bitmex.com"; // 필요 시 참고용
// EXPIRES 값 생성 (30초 만료 기준)
EXPIRES = nonceFactory.createValue();
// BitMEX 서명 규칙: VERB + ENDPOINT + EXPIRES
String data = VERB + ENDPOINT + String.valueOf(EXPIRES);
// HMAC signature 생성
return BD.digestString(data);
}
public String getAPI_SECRET() {
return API_SECRET;
}
public void setAPI_SECRET(String aPI_SECRET) {
API_SECRET = aPI_SECRET;
}
public String getAPI_KEY() {
return API_KEY;
}
public void setAPI_KEY(String aPI_KEY) {
API_KEY = aPI_KEY;
}
public Long getEXPIRES() {
return EXPIRES;
}
public void setEXPIRES(Long eXPIRES) {
EXPIRES = eXPIRES;
}
}
코드 핵심 정리
nonceFactory = new ExpirationTimeFactory(30)→ 30초 뒤 만료되는 값을 생성. EXPIRES 값으로 사용.data = VERB + ENDPOINT + EXPIRES→ BitMEX 인증 규칙에 맞게 서명 대상 문자열을 조합.BitmexDigest.createInstance(API_SECRET)→ API_SECRET을 사용해 HMAC 서명 유틸 인스턴스 생성.bitmex_signature()호출 시 →EXPIRES값도 새로 생성되므로, 인증 요청 보낼 때 함께 사용해야 함.
4. WebSocket(wss)에서 authKeyExpires 전송 예제
위에서 만든 SignatureUtil을 사용하면,
실제 WebSocket 클라이언트 코드에서는 다음과 같이 인증 메시지를 전송할 수 있습니다.
// SignatureUtil 생성 (초기화 시 API KEY/SECRET 주입)
SignatureUtil signatureUtil = new SignatureUtil("YOUR_API_KEY", "YOUR_API_SECRET");
// WebSocket 연결 이후, 인증 메시지 전송
String bitmex_signature = signatureUtil.bitmex_signature();
ws.sendText(
"{\"op\" : \"authKeyExpires\", " +
"\"args\" : [\"" + signatureUtil.getAPI_KEY() + "\"," +
signatureUtil.getEXPIRES() + "," +
"\"" + bitmex_signature + "\"]}"
);
여기서 중요한 점
bitmex_signature()호출 후에getEXPIRES()를 사용해야 합니다. → 서명과 EXPIRES가 반드시 같은 시점 기준이어야 하기 때문입니다.- JSON 문자열에서 API_KEY, EXPIRES, SIGNATURE 순서를 정확히 맞춰야 합니다.
- WebSocket 연결 후 가장 먼저 authKeyExpires를 보내 인증한 뒤,
개인 데이터 채널(예:
position,order)을 subscribe 하는 순서로 구현하는 것이 일반적입니다.
5. 실무에서 사용할 때 팁
- API_KEY / API_SECRET은 절대 코드에 하드코딩하지 말고, 환경변수 혹은 설정 파일에서 로딩하는 방식 권장
- EXPIRES는 너무 짧거나 너무 길지 않게 적당한 만료 시간으로 조정
- 실서비스에서는 로그 기록을 통해 인증 실패, 서명 오류 등을 추적
- 테스트 환경(테스트넷)과 운영 환경(mainnet) BitMEX URL을 분리해서 관리
6. 정리
이 글에서는 Java XChange 라이브러리를 활용한 BitMEX WebSocket 인증 서명 구현 방법을 정리했습니다. 핵심은 다음과 같습니다.
BitmexDigest로 HMAC signature 생성ExpirationTimeFactory로 EXPIRES 값 생성VERB + ENDPOINT + EXPIRES문자열을 서명하여 WebSocket 인증에 사용authKeyExpires메시지로 API_KEY, EXPIRES, SIGNATURE 전송
위 예제 코드를 그대로 가져가서 프로젝트에 맞게 API 키/시크릿 관리 방식만 바꿔주면, 빠르게 BitMEX WebSocket 인증 로직을 구축할 수 있습니다.
댓글
댓글 쓰기