@readerseye2/cr_type 1.0.185 → 1.0.188

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  import { ChatMessageReadRequest, ChatMessageRefreshRequest, MessageRequest } from "./socket-message.types";
2
2
  import { SessionDataPayload } from "./reading-section.types";
3
- import { ViewerOpenPayload, ViewerClosePayload, SessionHistoryListPayload, SessionHistoryGetPayload, SessionHistoryDeletePayload, UnifiedChunksGetPayload, UnifiedSegmentGetPayload } from "./unified-session.types";
3
+ import { ViewerOpenPayload, ViewerClosePayload, SessionHistoryListPayload, SessionHistoryGetPayload, SessionHistoryDeletePayload, UnifiedChunksGetPayload, UnifiedSegmentGetPayload, LiveBatchPayload } from "./unified-session.types";
4
4
  import { ReadingProgressReport } from "../book/child-reading-progress.type";
5
5
  export interface ClientToServerEvents {
6
6
  'chat-message:send': (msg: MessageRequest) => void;
@@ -10,7 +10,7 @@ export interface ClientToServerEvents {
10
10
  'session:open': (payload: ViewerOpenPayload) => void;
11
11
  /** 뷰어 닫힘 (세션 종료) */
12
12
  'session:close': (payload: ViewerClosePayload) => void;
13
- /** 5초 통합 데이터 (events + gaze + snapshot) */
13
+ /** 10초 통합 데이터 (events + gaze + snapshot) */
14
14
  'session:data': (payload: SessionDataPayload) => void;
15
15
  /** 자녀 세션 live 구독 (부모) */
16
16
  'live:subscribe': (payload: {
@@ -20,6 +20,12 @@ export interface ClientToServerEvents {
20
20
  'live:unsubscribe': (payload: {
21
21
  readingSessionId: string;
22
22
  }) => void;
23
+ /** 라이브 batch 전송 (CR_app → server, 100ms 주기) */
24
+ 'live:batch': (payload: LiveBatchPayload) => void;
25
+ /** 라이브 mid-join 초기 상태 요청 (watcher → server) */
26
+ 'live:request-initial': (payload: {
27
+ readingSessionId: string;
28
+ }) => void;
23
29
  /** 읽기 진행 보고 (5초 주기 자동저장) */
24
30
  'progress:reading-save': (payload: ReadingProgressReport) => void;
25
31
  /** 자녀 읽기 상태 구독 시작 */
@@ -60,6 +66,16 @@ export interface ClientToServerEvents {
60
66
  'webrtc:hangup': (payload: {
61
67
  targetSocketId: string;
62
68
  }) => void;
69
+ /**
70
+ * 자녀→부모 peer 오류 통지.
71
+ * 자녀 단말에 카메라가 없거나, answer 생성 실패 등으로 offer를 처리할 수 없을 때 발신.
72
+ * 부모는 watchdog timeout 대신 즉시 명확한 에러 메시지를 받는다.
73
+ */
74
+ 'webrtc:peer-error': (payload: {
75
+ targetParentSocketId: string;
76
+ reason: 'camera-unavailable' | 'no-video-track' | 'offer-failed';
77
+ message?: string;
78
+ }) => void;
63
79
  /**
64
80
  * WebRTC 진단 정보 (부모→서버, 단방향)
65
81
  * - iceCandidateType: 부모 측 selected candidate pair의 local candidate type
@@ -1,6 +1,6 @@
1
1
  import { MessageReadResponse, MessageResponse, NoticeMessageResult } from "./socket-message.types";
2
2
  import { ConnectedUser, ConnectedUsersGrouped } from "./connected-user.types";
3
- import { UnifiedSessionInfo, SessionSegmentChangedPayload, SessionHistoryListResult, SessionHistoryGetResult, UnifiedChunksResult, UnifiedSegmentResult, SessionHistoryDeleteResult } from "./unified-session.types";
3
+ import { UnifiedSessionInfo, SessionSegmentChangedPayload, SessionHistoryListResult, SessionHistoryGetResult, UnifiedChunksResult, UnifiedSegmentResult, SessionHistoryDeleteResult, LiveBatchPayload, LiveInitialPayload, LiveChunkRolledPayload, LiveEmitToggle } from "./unified-session.types";
4
4
  import { LiveReadingState } from "../book/child-reading-progress.type";
5
5
  /** WebRTC ICE 서버 설정 (STUN/TURN) */
6
6
  export interface IceServerConfig {
@@ -33,7 +33,7 @@ export interface ServerToClientEvents {
33
33
  'session:error': (payload: {
34
34
  message: string;
35
35
  }) => void;
36
- /** 새 chunk 저장 알림 (5초마다) — 데이터는 기존 API로 fetch */
36
+ /** 새 chunk 저장 알림 (10초마다) — 데이터는 기존 API로 fetch */
37
37
  'live:chunk-notify': (payload: {
38
38
  readingSessionId: string;
39
39
  segmentIndex: number;
@@ -46,6 +46,16 @@ export interface ServerToClientEvents {
46
46
  readingSessionId: string;
47
47
  durationMs: number;
48
48
  }) => void;
49
+ /** 라이브 batch fanout (server → watchers in live:${id} room) */
50
+ 'live:batch': (payload: LiveBatchPayload) => void;
51
+ /** 라이브 mid-join 초기 상태 응답 (server → 단일 watcher) */
52
+ 'live:initial': (payload: LiveInitialPayload) => void;
53
+ /** chunk 경계 anchor 갱신 (server → watchers) */
54
+ 'live:chunk-rolled': (payload: LiveChunkRolledPayload) => void;
55
+ /** 시청자 1명 이상 → publisher emit 시작 (Phase 7) */
56
+ 'live:start-emit': (payload: LiveEmitToggle) => void;
57
+ /** 시청자 0명 → publisher emit 정지 (Phase 7) */
58
+ 'live:stop-emit': (payload: LiveEmitToggle) => void;
49
59
  /** 자녀(같은 family room)가 소켓에 연결됨 */
50
60
  'user:connected': (payload: {
51
61
  user: ConnectedUser;
@@ -103,6 +113,16 @@ export interface ServerToClientEvents {
103
113
  fromIdx: number;
104
114
  fromSocketId: string;
105
115
  }) => void;
116
+ /**
117
+ * 자녀 측 peer 오류 수신 (부모 측).
118
+ * 자녀 단말에 카메라가 없거나 offer 처리 실패 시 즉시 통지된다.
119
+ */
120
+ 'webrtc:peer-error': (payload: {
121
+ fromChildIdx: number;
122
+ fromSocketId: string;
123
+ reason: 'camera-unavailable' | 'no-video-track' | 'offer-failed';
124
+ message?: string;
125
+ }) => void;
106
126
  }
107
127
  export interface NoticeToClientEvents {
108
128
  'notice-message:result': (payload: NoticeMessageResult) => void;
@@ -308,3 +308,49 @@ export interface ActiveUnifiedSegment {
308
308
  totalEvents: number;
309
309
  totalGazeSamples: number;
310
310
  }
311
+ /**
312
+ * 라이브 batch 페이로드 (CR_app → server → watchers).
313
+ * - events 있으면 reliable emit, gaze만이면 volatile emit
314
+ * - gazeSamples: flat [x, y, t, x, y, t, ...] (저장과 동일 포맷)
315
+ */
316
+ export interface LiveBatchPayload {
317
+ readingSessionId: string;
318
+ /** flat [x, y, t, ...]. 100ms 동안 누적된 gaze samples */
319
+ gazeSamples?: number[];
320
+ /** 100ms 동안 발생한 viewer events */
321
+ events?: ViewerEvent[];
322
+ /** publisher 측 batch 종료 timestamp */
323
+ clientTs: number;
324
+ }
325
+ /**
326
+ * Watcher mid-join 응답 (server → 단일 watcher).
327
+ * chunkStartSnapshot은 anchor, bufferedEvents/bufferedGaze는 chunk 시작~now 누적.
328
+ */
329
+ export interface LiveInitialPayload {
330
+ readingSessionId: string;
331
+ segmentIndex: number;
332
+ chunkStartTs: number;
333
+ chunkStartSnapshot: ViewerSnapshot;
334
+ /** chunk 시작 ~ 현재 누적 events */
335
+ bufferedEvents: ViewerEvent[];
336
+ /** chunk 시작 ~ 현재 누적 gaze */
337
+ bufferedGaze: GazeBatch[];
338
+ /** 서버 응답 시각 (clock sync용) */
339
+ serverTs: number;
340
+ }
341
+ /**
342
+ * Chunk 경계에서 새 anchor 통지 (server → watchers).
343
+ * watcher는 이 신호로 currentChunkStartTs 갱신 + snapshot 재적용.
344
+ */
345
+ export interface LiveChunkRolledPayload {
346
+ readingSessionId: string;
347
+ segmentIndex: number;
348
+ newChunkStartTs: number;
349
+ newChunkStartSnapshot: ViewerSnapshot;
350
+ }
351
+ /**
352
+ * Publisher → emit on/off 신호 (시청자 0명 최적화, Phase 7).
353
+ */
354
+ export interface LiveEmitToggle {
355
+ readingSessionId: string;
356
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@readerseye2/cr_type",
3
- "version": "1.0.185",
3
+ "version": "1.0.188",
4
4
  "description": "CheckReading shared TypeScript types",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",