가이드 목록 | 이전: 프록시 패턴 | 다음: TLS와 WSS
Transport 가이드¶
이 장이 답하는 것 —
tcp://·inproc://·tls://·wss://등 endpoint 형식과 transport별 특성을 비교한다. 각 socket에 적용되는 정확한 조건은 socket 스펙이 소유한다.
1. Transport 종류¶
| Transport | URI 형식 | 예시 | 암호화 | 핸드셰이크 |
|---|---|---|---|---|
| tcp | tcp://host:port |
tcp://127.0.0.1:5555 |
- | - |
| ipc | ipc://path |
ipc:///tmp/test.ipc |
- | - |
| inproc | inproc://name |
inproc://workers |
- | - |
| ws | ws://host:port/path |
ws://127.0.0.1:8080 |
- | O |
| wss | wss://host:port/path |
wss://server:8443 |
O | O |
| tls | tls://host:port |
tls://server:5555 |
O | O |
소켓별 Transport 지원¶
| Transport | PAIR | PUB/SUB | DEALER | ROUTER | STREAM |
|---|---|---|---|---|---|
| tcp | O | O | O | O | O |
| ipc | O | O | O | O | O |
| inproc | O | O | O | O | O |
| tls | O | O | O | O | O |
| ws | O | O | O | O | O |
| wss | O | O | O | O | O |
- STREAM은 첫 bind 또는 connect 전에
ZLINK_STREAM_OPT_RECV_MODE를 RAW 또는 PACKET으로 설정한 뒤 bind와 connect를 모두 사용할 수 있다. 반대편은 raw socket/websocket client이거나 다른 STREAM socket이다. ws는 모든 zlink build에서 제공한다.tls는WITH_TLSbuild 옵션에 따라 제공하며,wss는 TLS를 켠 build에서 제공한다.zlink_has("tls")·zlink_has("wss")로 지원 여부를 확인한다.
2. TCP¶
표준 TCP/IP 네트워크 통신.
기본 사용법¶
/* Server: specific interface */
zlink_bind(socket, "tcp://192.168.1.10:5555");
/* Server: all interfaces */
zlink_bind(socket, "tcp://*:5555");
/* Client: IP address */
zlink_connect(socket, "tcp://127.0.0.1:5555");
/* Client: DNS name */
zlink_connect(socket, "tcp://server.example.com:5555");
와일드카드 포트 (자동 할당)¶
OS가 사용 가능한 포트를 자동으로 할당한다. 테스트나 동적 포트 환경에서 쓰기 좋다.
/* Use port 0 or * */
zlink_bind(socket, "tcp://127.0.0.1:*");
/* Query the assigned endpoint */
char endpoint[256];
size_t len = sizeof(endpoint);
zlink_get_option(socket, ZLINK_OPT_LAST_ENDPOINT, endpoint, &len);
/* endpoint = "tcp://127.0.0.1:53821" (example) */
/* Connect using the retrieved endpoint */
zlink_connect(other_socket, endpoint);
참고:
core/tests/integration/test_pair_tcp.cpp—bind_loopback_ipv4()와일드카드 바인드 패턴
DNS 이름 사용¶
connect 시 호스트명을 쓰면 내부적으로 DNS를 resolve한다.
주의: DNS resolve은 블로킹으로 동작한다. 프로덕션에서는 IP 주소를 권장한다. 참고:
core/tests/integration/test_pair_tcp.cpp—test_pair_tcp_connect_by_name()
에러 처리¶
/* bind 실패: 포트 이미 사용 중 */
zlink_bind_result_t bind_rc = zlink_bind(socket, "tcp://*:5555");
if (bind_rc == ZLINK_BIND_ADDR_IN_USE) {
printf("Port 5555 already in use\n");
}
/* connect 실패: 잘못된 주소 */
zlink_connect_result_t conn_rc = zlink_connect(
socket, "tcp://invalid:99999");
if (conn_rc != ZLINK_CONNECT_OK) {
printf("Connection failed: %d\n", (int)conn_rc);
}
특성¶
- TCP_NODELAY 활성화 (Nagle 알고리즘 비활성화)
- 투기적 쓰기(speculative write) — 동기 쓰기를 먼저 시도하고 실패하면 비동기로 전환
- 모아 쓰기(gather write) — 헤더와 바디를 한 번에 보내 시스템 콜 횟수를 줄임
투기적 쓰기 등 내부 최적화 상세는 architecture.md를 참고.
3. IPC¶
Unix 도메인 소켓 기반 로컬 프로세스 간 통신.
기본 사용법¶
/* Server */
zlink_bind(socket, "ipc:///tmp/myapp.ipc");
/* Client */
zlink_connect(socket, "ipc:///tmp/myapp.ipc");
와일드카드 바인드¶
/* IPC wildcard — auto-assigns a temporary path */
zlink_bind(socket, "ipc://*");
char endpoint[256];
size_t len = sizeof(endpoint);
zlink_get_option(socket, ZLINK_OPT_LAST_ENDPOINT, endpoint, &len);
참고:
core/tests/integration/test_router_multiple_dealers.cpp—zlink_bind(router, "ipc://*")
에러 처리¶
/* 경로 너무 김 */
zlink_bind_result_t rc = zlink_bind(
socket, "ipc:///very/long/path/.../endpoint.ipc");
if (rc == ZLINK_BIND_INTERNAL_ERROR) {
/* IPC 경로가 플랫폼 sun_path 한계 이상 — ENAMETOOLONG */
printf("IPC path exceeds platform sun_path limit\n");
}
참고:
core/tests/integration/test_pair_ipc.cpp—test_endpoint_too_long()
특성¶
- Windows를 제외한 platform에서 지원 (
ZLINK_HAVE_IPCbuild) - TCP 대비 낮은 오버헤드 (네트워크 스택 우회)
- 파일 경로 기반 주소 (경로는 플랫폼 sun_path 한계보다 짧아야 함)
4. inproc¶
프로세스 내(in-process) 통신. 가장 빠른 transport.
기본 사용법¶
/* bind와 connect 순서는 제한하지 않는다 */
zlink_bind(socket_a, "inproc://workers");
zlink_connect(socket_b, "inproc://workers");
connect가 먼저인 경우¶
/* 아직 bind되지 않은 endpoint에 connect — 성공하며 Core가 endpoint를 보류한다 */
zlink_connect_result_t rc = zlink_connect(socket_b, "inproc://workers");
/* 같은 context에서 bind가 뒤에 오면 그때 연결된다 */
zlink_bind(socket_a, "inproc://workers");
특성¶
- 동일 context 내에서만 사용 가능
- bind와 connect 순서는 제한하지 않음 — connect가 먼저면 Core가 보류했다가 같은 context의 bind와 연결
- 잠금 없는(lock-free) 파이프 직접 연결 (네트워크 없음)
- 가장 낮은 지연시간, 가장 높은 처리량
참고:
core/tests/integration/test_pair_inproc.cpp— bind → connect → bounce 패턴
5. WebSocket (ws)¶
웹 브라우저 및 외부 클라이언트 연동.
기본 사용법¶
/* Server */
zlink_bind(socket, "ws://*:8080");
/* Client */
zlink_connect(socket, "ws://server:8080");
/* Wildcard port */
zlink_bind(socket, "ws://127.0.0.1:*");
char endpoint[256];
size_t len = sizeof(endpoint);
zlink_get_option(socket, ZLINK_OPT_LAST_ENDPOINT, endpoint, &len);
참고:
core/tests/integration/test_stream_socket.cpp—test_stream_ws_basic()
특성¶
- RFC 6455 준수
- Beast 라이브러리 기반
- 바이너리 프레임 모드 (Opcode=0x02)
- 64KB write buffer
6. WebSocket + TLS (wss)¶
암호화된 WebSocket 통신.
기본 사용법¶
/* Server */
zlink_set_tls_server(socket, cert_path, key_path, 0);
zlink_bind(socket, "wss://*:8443");
/* Client */
zlink_set_tls_client(socket, ca_path, "localhost", 0);
zlink_connect(socket, "wss://server:8443");
참고:
core/tests/integration/test_stream_socket.cpp—test_stream_wss_basic()
ws 대비 추가 설정¶
| 설정 | ws | wss |
|---|---|---|
zlink_set_tls_server() (서버 cert+key) |
- | 필수 |
zlink_set_tls_client() (클라이언트 CA+hostname+trust) |
- | 권장 |
7. TLS¶
네이티브 TLS 암호화 통신.
기본 사용법¶
/* Server */
zlink_set_tls_server(socket, "/path/to/cert.pem", "/path/to/key.pem", 0);
zlink_bind(socket, "tls://*:5555");
/* Client */
zlink_set_tls_client(socket, "/path/to/ca.pem", "server", 1);
zlink_connect(socket, "tls://server:5555");
상세 TLS 설정은 TLS 보안 가이드를 참고.
8. Transport 제약사항¶
| 제약 | 설명 |
|---|---|
| STREAM | 첫 bind/connect 전에 ZLINK_STREAM_OPT_RECV_MODE 설정 필요; bind·connect 모두 지원 |
| inproc | bind와 connect 순서 제한 없음 (connect가 먼저면 보류 뒤 bind와 연결) |
| ipc | Windows를 제외한 platform에서 지원 |
| inproc context | 동일 context 내에서만 사용 |
| IPC 경로 | Unix 도메인 소켓 경로는 플랫폼 sun_path 한계보다 짧아야 함 |
9. Transport 선택 가이드¶
| 사용 사례 | 추천 Transport | 비고 |
|---|---|---|
| 스레드 간 통신 | inproc | 최고 성능 |
| 로컬 프로세스 간 (Unix) | ipc | TCP 대비 낮은 오버헤드 |
| 로컬 프로세스 간 (Windows) | tcp | IPC 미지원 |
| 서버 간 통신 | tcp | 표준 네트워크 통신 |
| 암호화 통신 | tls | 네이티브 TLS |
| 웹 클라이언트 | ws 또는 wss | WebSocket |
| 최고 성능 순서 | inproc > ipc > tcp > ws | 오버헤드 증가 순 |
10. bind vs connect¶
기본 원칙¶
- bind: 안정적인 주소를 제공하는 쪽 (서버, 잘 알려진 주소)
- connect: 상대방 주소를 알고 연결하는 쪽 (클라이언트)
다중 bind/connect¶
하나의 소켓에 여러 엔드포인트를 bind하거나 connect할 수 있다.
/* Multiple bind — listen on multiple interfaces */
zlink_bind(router, "tcp://192.168.1.10:5555");
zlink_bind(router, "tcp://10.0.0.1:5555");
zlink_bind(router, "ipc:///tmp/router.ipc");
/* Multiple connect — connect to multiple servers */
zlink_connect(dealer, "tcp://server1:5555");
zlink_connect(dealer, "tcp://server2:5555");
ZLINK_OPT_LAST_ENDPOINT¶
와일드카드 바인드 후 실제 할당된 엔드포인트를 조회한다.
zlink_bind(socket, "tcp://127.0.0.1:*");
char endpoint[256];
size_t len = sizeof(endpoint);
zlink_get_option(socket, ZLINK_OPT_LAST_ENDPOINT, endpoint, &len);
printf("Bound endpoint: %s\n", endpoint);
성능 비교는 성능 가이드를 참고.