AI용 빠른 참조
IOSignal JavaScript 7.2.0 · 문서 기준일 2026-10-19 · sourceCommit cd03bbf1606098571bac3e03d02459e1a9a86a5f (iosignal 저장소 main, Node.js 22.16.0 이상). Arduino·CLI·Boho는 별도 패키지입니다.
이 페이지는 한 페이지 요약입니다. 세부 동작과 예외는 AI 안내, 클라이언트 API, 서버 API에서 확인하세요. 설치된 버전이 7.2.0과 다르면 해당 버전의 타입·구현·테스트를 기준으로 판단합니다.
가져오기와 설치
| 환경 | 코드 |
|---|---|
| Node.js | import { IO, Server } from 'iosignal' |
| 브라우저 번들러 | import IO from 'iosignal/io' |
| 브라우저 CDN | https://cdn.jsdelivr.net/npm/iosignal@7.2.0/dist/browser/iife/io.js |
| 설치 | npm install --save-exact iosignal@7.2.0 |
iosignal 루트 엔트리는 Node.js용입니다. 브라우저에서 import { IO } from 'iosignal'을 사용하지 마세요. 브라우저는 번들러 경로 iosignal/io 또는 CDN의 IIFE·ESM 빌드를 사용합니다.
연결과 수명주기
import { IO } from 'iosignal';
const io = new IO();
const tag = 'room#chat';
io.on('message', (tag, ...args) => {
// 채널 구독과 CID 발행 구독의 공통 수신
});
io.on('@', (tag, ...args) => {
// 모든 직접 시그널 수신 (구독 불필요)
});
io.on('ready', () => {
io.subscribe(tag); // 수동 구독은 ready마다 등록
io.signal(tag, { hello: io.cid }); // ready 이후 송신
});
// 일반 태그는 listen()으로 핸들러와 자동 구독을 함께 등록합니다.
io.listen('alarm#state', (tag, ...args) => {
console.log(tag, ...args);
});
io.open('ws://localhost:7777');
- 소켓
open과 IOSignalready는 다릅니다. CID 사용·수동 구독·송신은ready이후에 수행합니다. ready는 재접속마다 다시 발생합니다.io.cid는 연결마다 달라질 수 있으므로 매번 다시 읽습니다.- 수동
subscribe()는 재접속 후 유지되지 않습니다.ready핸들러에서 다시 등록합니다. - 일반 태그의
listen()은ready시점과 재접속 시 자동으로 구독합니다. 직접 수신 태그(@,@topic)는 구독하지 않습니다. on()은 핸들러만 등록하며 서버 구독을 보내지 않습니다.
태그
| 용도 | 송신 태그 | 구독 태그 | 수신 핸들러의 tag |
|---|---|---|---|
| 일반 채널 | room#topic | room#topic | room#topic |
| B에게 직접 송신 | B@topic | 필요 없음 | @topic |
| CID 발행 | @topic | A@topic | A@topic |
| 홈채널 | #topic | #topic | #topic |
- 태그는 UTF-8 기준 최대 255 bytes입니다. 문자열
.length(문자 수)와 다릅니다. #topic은 외부 IP로 구분되는 HOME CHANNEL이며 인증·신뢰 경계가 아닙니다.room#topic처럼#앞의room은 채널, 뒤는 토픽입니다. 계층형 토픽은 지원하지 않습니다.- 직접 수신에
subscribe('@topic')또는unsubscribe('@topic')를 호출하면TypeError입니다.on()·listen()으로 등록합니다.A@topic은 CID 발행 구독이므로 허용합니다.
payload
io.signal('room'); // EMPTY → (tag)
io.signal('room', 'hello'); // TEXT → (tag, 'hello')
io.signal('room', new Uint8Array([1, 2])); // BINARY → (tag, 바이너리)
io.signal('room', {value: 42}); // OBJECT → (tag, {value: 42})
io.signal('room', 'value', 42); // MJSON → (tag, 'value', 42)
io.signal('room', 42); // TEXT → (tag, '42')
- 숫자 하나는 TEXT로 변환됩니다. 숫자를 유지하려면 객체나 여러 인자를 사용합니다.
- OBJECT/MJSON/MBA는 JS에서 자동 복원되지만 Arduino 콜백에는 유형값·원시 바이트·길이만 전달됩니다.
signal()호출은 상대의 업무 처리 완료를 뜻하지 않습니다. 필요하면 응용 메시지로 응답을 설계합니다.
직접 수신
// 상대에게 직접 송신
io.signal(peerCid + '@rtc', {type: 'offer', sdp});
// 수신: '@' 다음에 정확한 '@rtc'가 발생하며 'message'로는 전달되지 않습니다.
io.on('@rtc', (tag, message) => {
console.log(tag, message); // '@rtc', {type: 'offer', sdp}
});
'@'와 '@rtc'에 같은 처리를 등록하면 하나의 메시지를 두 번 처리할 수 있습니다. 직접 수신에는 서버 구독이 필요하지 않습니다.
quota와 크기 제한
- quota는 라이브러리가 모든 배포에 강제하는 고정값이 아니라 서버 운영자가 설정하는 정책입니다.
ready이후io.level과io.quota.signalSize로 현재 연결에 적용된 값을 확인합니다. 특정 값을 코드에 하드코딩하지 않습니다.- 배포 버전의 기본값은
serverOption을 참고용으로만 볼 수 있습니다. 운영 환경에서는defaultQuotaIndex,useQuota, 인증 레벨을 직접 설정합니다. - 태그 255 bytes는 프로토콜 제한이며 quota와 다릅니다.
signalSize를 넘는 전송은 보내지 않고over_size이벤트가 발생할 수 있습니다. 큰 payload는 보내기 전에 크기를 확인합니다.
재접속
io.on('ready', () => {
io.subscribe(tag); // 수동 구독 재등록
rebuildPeers(io.cid); // 피어 목록·방 상태를 새 CID 기준으로 재구성
});
- 공개 서버의 초기 리디렉션은
ready이전에 일어날 수 있습니다.ready이후의 단절과 구분하고 연결 대기 시간에 상한을 둡니다. - CID를 키로 저장한 피어 목록·방 상태는 재접속 후 그대로 유효하다고 가정하지 않습니다.
listen()으로 등록한 일반 태그 구독은 라이브러리가 자동으로 다시 보냅니다.- 예시의
rebuildPeers()는 라이브러리 API가 아니라 앱이 구현하는 함수입니다. - IO 인스턴스를 단독 소유한 컴포넌트가 사라지면
destroy()를 호출합니다. 공유 인스턴스라면link()로 연결한 컴포넌트만unlinkAll(component)로 해제합니다.unlinkAll()은 해당 컴포넌트가link()로 등록한 핸들러와 그 링크가 소유한 구독만 정리하며,on()·listen()으로 등록한 핸들러는 제거하지 않습니다.
Arduino
- Arduino는 별도 라이브러리이며 JS 객체를 자동 복원하지 않습니다.
onMessage콜백의 유형값·원시 바이트·길이를 앱에서 파싱합니다. - 태그와 payload 크기 제한은 같은 프로토콜 규칙을 따릅니다. 보드의 메모리와 버퍼 크기를 함께 확인합니다.
- 연결 유지 호출과 보드별 배선은 Arduino 소개와 설치를 따릅니다.
AI에게 작업을 맡길 때
- 문서에 없는 API를 추측하지 말고 설치 버전의 타입·소스·테스트로 확인합니다.
- 실행 환경, 설치 버전, sourceCommit, 실행 명령, 실제 테스트와 미검증 범위를 함께 보고합니다.
- 라이브러리가 보장하는 동작과 앱이 선택한 규칙(방 인원, 권한, 메시지 형식)을 구분합니다.