@simplysm/service-common 14.0.1 → 14.0.4
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.
- package/README.md +233 -0
- package/dist/protocol/create-service-protocol.d.ts.map +1 -1
- package/dist/protocol/create-service-protocol.js +3 -2
- package/dist/protocol/create-service-protocol.js.map +1 -1
- package/dist/protocol/protocol.types.d.ts +2 -10
- package/dist/protocol/protocol.types.d.ts.map +1 -1
- package/package.json +6 -3
- package/src/protocol/create-service-protocol.ts +3 -2
- package/src/protocol/protocol.types.ts +0 -11
package/README.md
ADDED
|
@@ -0,0 +1,233 @@
|
|
|
1
|
+
# @simplysm/service-common
|
|
2
|
+
|
|
3
|
+
Shared service protocol and types -- binary protocol V2 with chunking, message types, service event definitions.
|
|
4
|
+
|
|
5
|
+
This package provides the platform-neutral foundation shared by both `@simplysm/service-client` and `@simplysm/service-server`.
|
|
6
|
+
|
|
7
|
+
## API
|
|
8
|
+
|
|
9
|
+
| Export | Kind | Category | Description |
|
|
10
|
+
|--------|------|----------|-------------|
|
|
11
|
+
| `PROTOCOL_CONFIG` | const | Protocol | Protocol configuration constants (max size, chunk size, GC interval, expiry) |
|
|
12
|
+
| `ServiceMessage` | type | Protocol | Union of all message types (client + server) |
|
|
13
|
+
| `ServiceServerMessage` | type | Protocol | Union of server-to-client message types |
|
|
14
|
+
| `ServiceServerRawMessage` | type | Protocol | Server raw message (includes progress) |
|
|
15
|
+
| `ServiceClientMessage` | type | Protocol | Union of client-to-server message types |
|
|
16
|
+
| `ServiceProgressMessage` | interface | Protocol | Chunk receive progress notification |
|
|
17
|
+
| `ServiceErrorMessage` | interface | Protocol | Error notification from server |
|
|
18
|
+
| `ServiceAuthMessage` | interface | Protocol | Authentication message from client |
|
|
19
|
+
| `ServiceRequestMessage` | interface | Protocol | Service method request from client |
|
|
20
|
+
| `ServiceResponseMessage` | interface | Protocol | Service method response from server |
|
|
21
|
+
| `ServiceAddEventListenerMessage` | interface | Protocol | Add event listener request |
|
|
22
|
+
| `ServiceRemoveEventListenerMessage` | interface | Protocol | Remove event listener request |
|
|
23
|
+
| `ServiceGetEventListenerInfosMessage` | interface | Protocol | Get event listener info list request |
|
|
24
|
+
| `ServiceEmitEventMessage` | interface | Protocol | Emit event request |
|
|
25
|
+
| `ServiceEventMessage` | interface | Protocol | Event notification from server |
|
|
26
|
+
| `ServiceProtocol` | interface | Protocol | Protocol encoder/decoder interface |
|
|
27
|
+
| `ServiceMessageDecodeResult` | type | Protocol | Decode result (complete or progress) |
|
|
28
|
+
| `createServiceProtocol` | function | Protocol | Create a protocol encoder/decoder instance |
|
|
29
|
+
| `OrmService` | interface | Service Types | ORM service interface (connect, transaction, query) |
|
|
30
|
+
| `DbConnOptions` | type | Service Types | Database connection options |
|
|
31
|
+
| `AutoUpdateService` | interface | Service Types | Auto-update service interface |
|
|
32
|
+
| `ServiceUploadResult` | interface | Types | File upload result |
|
|
33
|
+
| `ServiceEventDef` | interface | Definitions | Event definition created by `defineEvent()` |
|
|
34
|
+
| `defineEvent` | function | Definitions | Define a typed service event |
|
|
35
|
+
|
|
36
|
+
## Protocol
|
|
37
|
+
|
|
38
|
+
### PROTOCOL_CONFIG
|
|
39
|
+
|
|
40
|
+
Protocol configuration constants.
|
|
41
|
+
|
|
42
|
+
```ts
|
|
43
|
+
import { PROTOCOL_CONFIG } from "@simplysm/service-common";
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
| Field | Type | Default | Description |
|
|
47
|
+
|-------|------|---------|-------------|
|
|
48
|
+
| `MAX_TOTAL_SIZE` | `number` | `104,857,600` (100 MB) | Maximum message size |
|
|
49
|
+
| `SPLIT_MESSAGE_SIZE` | `number` | `3,145,728` (3 MB) | Chunking threshold -- messages larger than this are split |
|
|
50
|
+
| `CHUNK_SIZE` | `number` | `307,200` (300 KB) | Size of each chunk |
|
|
51
|
+
| `GC_INTERVAL` | `number` | `10,000` (10 s) | Garbage collection interval for incomplete messages |
|
|
52
|
+
| `EXPIRE_TIME` | `number` | `60,000` (60 s) | Expiry time for incomplete chunked messages |
|
|
53
|
+
|
|
54
|
+
### Message Types
|
|
55
|
+
|
|
56
|
+
All messages exchanged between client and server are strongly typed.
|
|
57
|
+
|
|
58
|
+
#### Client-to-Server Messages
|
|
59
|
+
|
|
60
|
+
| Interface | `name` Field | Description |
|
|
61
|
+
|-----------|-------------|-------------|
|
|
62
|
+
| `ServiceAuthMessage` | `"auth"` | Authenticate with a token string |
|
|
63
|
+
| `ServiceRequestMessage` | `` `${service}.${method}` `` | Call a service method with parameters |
|
|
64
|
+
| `ServiceAddEventListenerMessage` | `"evt:add"` | Register an event listener with key, event name, and filter info |
|
|
65
|
+
| `ServiceRemoveEventListenerMessage` | `"evt:remove"` | Unregister an event listener by key |
|
|
66
|
+
| `ServiceGetEventListenerInfosMessage` | `"evt:gets"` | Query listener info list for an event name |
|
|
67
|
+
| `ServiceEmitEventMessage` | `"evt:emit"` | Emit an event to specific listener keys |
|
|
68
|
+
|
|
69
|
+
#### Server-to-Client Messages
|
|
70
|
+
|
|
71
|
+
| Interface | `name` Field | Description |
|
|
72
|
+
|-----------|-------------|-------------|
|
|
73
|
+
| `ServiceProgressMessage` | `"progress"` | Chunk receive progress (`totalSize`, `completedSize`) |
|
|
74
|
+
| `ServiceResponseMessage` | `"response"` | Service method return value |
|
|
75
|
+
| `ServiceErrorMessage` | `"error"` | Error with name, message, code, optional stack/detail/cause |
|
|
76
|
+
| `ServiceEventMessage` | `"evt:on"` | Event broadcast to listener keys with data |
|
|
77
|
+
|
|
78
|
+
### ServiceProtocol
|
|
79
|
+
|
|
80
|
+
Binary protocol V2 interface. Header: 28 bytes (UUID 16 + TotalSize 8 + Index 4), body: JSON. Auto-chunks messages exceeding 3 MB into 300 KB chunks. Maximum message size: 100 MB.
|
|
81
|
+
|
|
82
|
+
```ts
|
|
83
|
+
interface ServiceProtocol {
|
|
84
|
+
encode(uuid: string, message: ServiceMessage): { chunks: Bytes[]; totalSize: number };
|
|
85
|
+
decode<T extends ServiceMessage>(bytes: Bytes): ServiceMessageDecodeResult<T>;
|
|
86
|
+
dispose(): void;
|
|
87
|
+
}
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
| Method | Parameters | Return | Description |
|
|
91
|
+
|--------|-----------|--------|-------------|
|
|
92
|
+
| `encode` | `uuid: string`, `message: ServiceMessage` | `{ chunks: Bytes[]; totalSize: number }` | Encode a message into binary chunks |
|
|
93
|
+
| `decode` | `bytes: Bytes` | `ServiceMessageDecodeResult<T>` | Decode received bytes; returns `"complete"` or `"progress"` |
|
|
94
|
+
| `dispose` | -- | `void` | Clean up internal GC timers |
|
|
95
|
+
|
|
96
|
+
### ServiceMessageDecodeResult\<TMessage\>
|
|
97
|
+
|
|
98
|
+
```ts
|
|
99
|
+
type ServiceMessageDecodeResult<TMessage extends ServiceMessage> =
|
|
100
|
+
| { type: "complete"; uuid: string; message: TMessage }
|
|
101
|
+
| { type: "progress"; uuid: string; totalSize: number; completedSize: number };
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
- `"complete"` -- all chunks received; the full message is available.
|
|
105
|
+
- `"progress"` -- chunked message still in progress.
|
|
106
|
+
|
|
107
|
+
### createServiceProtocol
|
|
108
|
+
|
|
109
|
+
```ts
|
|
110
|
+
function createServiceProtocol(): ServiceProtocol;
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
Creates a binary protocol V2 encoder/decoder instance.
|
|
114
|
+
|
|
115
|
+
## Service Types
|
|
116
|
+
|
|
117
|
+
### OrmService
|
|
118
|
+
|
|
119
|
+
ORM service interface. Supports MySQL, MSSQL, and PostgreSQL.
|
|
120
|
+
|
|
121
|
+
```ts
|
|
122
|
+
interface OrmService {
|
|
123
|
+
getInfo(opt: DbConnOptions & { configName: string }): Promise<{ dialect: Dialect; database?: string; schema?: string }>;
|
|
124
|
+
connect(opt: DbConnOptions & { configName: string }): Promise<number>;
|
|
125
|
+
close(connId: number): Promise<void>;
|
|
126
|
+
beginTransaction(connId: number, isolationLevel?: IsolationLevel): Promise<void>;
|
|
127
|
+
commitTransaction(connId: number): Promise<void>;
|
|
128
|
+
rollbackTransaction(connId: number): Promise<void>;
|
|
129
|
+
executeParametrized(connId: number, query: string, params?: unknown[]): Promise<unknown[][]>;
|
|
130
|
+
executeDefs(connId: number, defs: QueryDef[], options?: (ResultMeta | undefined)[]): Promise<unknown[][]>;
|
|
131
|
+
bulkInsert(connId: number, tableName: string, columnDefs: Record<string, ColumnMeta>, records: Record<string, unknown>[]): Promise<void>;
|
|
132
|
+
}
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
| Method | Parameters | Return | Description |
|
|
136
|
+
|--------|-----------|--------|-------------|
|
|
137
|
+
| `getInfo` | `opt: DbConnOptions & { configName: string }` | `Promise<{ dialect; database?; schema? }>` | Get database dialect and schema info |
|
|
138
|
+
| `connect` | `opt: DbConnOptions & { configName: string }` | `Promise<number>` | Open a connection; returns connection ID |
|
|
139
|
+
| `close` | `connId: number` | `Promise<void>` | Close a connection |
|
|
140
|
+
| `beginTransaction` | `connId: number`, `isolationLevel?: IsolationLevel` | `Promise<void>` | Begin a transaction |
|
|
141
|
+
| `commitTransaction` | `connId: number` | `Promise<void>` | Commit the current transaction |
|
|
142
|
+
| `rollbackTransaction` | `connId: number` | `Promise<void>` | Rollback the current transaction |
|
|
143
|
+
| `executeParametrized` | `connId: number`, `query: string`, `params?: unknown[]` | `Promise<unknown[][]>` | Execute a parameterized query |
|
|
144
|
+
| `executeDefs` | `connId: number`, `defs: QueryDef[]`, `options?: (ResultMeta \| undefined)[]` | `Promise<unknown[][]>` | Execute query definitions |
|
|
145
|
+
| `bulkInsert` | `connId: number`, `tableName: string`, `columnDefs: Record<string, ColumnMeta>`, `records: Record<string, unknown>[]` | `Promise<void>` | Bulk insert records |
|
|
146
|
+
|
|
147
|
+
### DbConnOptions
|
|
148
|
+
|
|
149
|
+
```ts
|
|
150
|
+
type DbConnOptions = { configName?: string; config?: Record<string, unknown> };
|
|
151
|
+
```
|
|
152
|
+
|
|
153
|
+
| Field | Type | Description |
|
|
154
|
+
|-------|------|-------------|
|
|
155
|
+
| `configName` | `string?` | Configuration name to look up |
|
|
156
|
+
| `config` | `Record<string, unknown>?` | Inline configuration object |
|
|
157
|
+
|
|
158
|
+
### AutoUpdateService
|
|
159
|
+
|
|
160
|
+
Auto-update service interface. Retrieves the latest version information for client applications.
|
|
161
|
+
|
|
162
|
+
```ts
|
|
163
|
+
interface AutoUpdateService {
|
|
164
|
+
getLastVersion(platform: string): Promise<{ version: string; downloadPath: string } | undefined>;
|
|
165
|
+
}
|
|
166
|
+
```
|
|
167
|
+
|
|
168
|
+
| Method | Parameters | Return | Description |
|
|
169
|
+
|--------|-----------|--------|-------------|
|
|
170
|
+
| `getLastVersion` | `platform: string` | `Promise<{ version: string; downloadPath: string } \| undefined>` | Get latest version info for a platform |
|
|
171
|
+
|
|
172
|
+
## Types
|
|
173
|
+
|
|
174
|
+
### ServiceUploadResult
|
|
175
|
+
|
|
176
|
+
File upload result containing server-side storage information.
|
|
177
|
+
|
|
178
|
+
```ts
|
|
179
|
+
interface ServiceUploadResult {
|
|
180
|
+
path: string;
|
|
181
|
+
filename: string;
|
|
182
|
+
size: number;
|
|
183
|
+
}
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
| Field | Type | Description |
|
|
187
|
+
|-------|------|-------------|
|
|
188
|
+
| `path` | `string` | Server-side storage path |
|
|
189
|
+
| `filename` | `string` | Original file name |
|
|
190
|
+
| `size` | `number` | File size in bytes |
|
|
191
|
+
|
|
192
|
+
## Definitions
|
|
193
|
+
|
|
194
|
+
### ServiceEventDef\<TInfo, TData\>
|
|
195
|
+
|
|
196
|
+
Event definition created by `defineEvent()`. The `$info` and `$data` fields are type-only markers (not used at runtime).
|
|
197
|
+
|
|
198
|
+
```ts
|
|
199
|
+
interface ServiceEventDef<TInfo = unknown, TData = unknown> {
|
|
200
|
+
eventName: string;
|
|
201
|
+
readonly $info: TInfo;
|
|
202
|
+
readonly $data: TData;
|
|
203
|
+
}
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
| Field | Type | Description |
|
|
207
|
+
|-------|------|-------------|
|
|
208
|
+
| `eventName` | `string` | Event name identifier |
|
|
209
|
+
| `$info` | `TInfo` | Type-only marker for listener filter info |
|
|
210
|
+
| `$data` | `TData` | Type-only marker for event payload data |
|
|
211
|
+
|
|
212
|
+
### defineEvent
|
|
213
|
+
|
|
214
|
+
```ts
|
|
215
|
+
function defineEvent<TInfo = unknown, TData = unknown>(eventName: string): ServiceEventDef<TInfo, TData>;
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
Define a typed service event for use with the event system.
|
|
219
|
+
|
|
220
|
+
```ts
|
|
221
|
+
import { defineEvent } from "@simplysm/service-common";
|
|
222
|
+
|
|
223
|
+
// Define an event with typed info and data
|
|
224
|
+
const MyEvent = defineEvent<{ userId: number }, { message: string }>("MyEvent");
|
|
225
|
+
|
|
226
|
+
// Server: emit the event
|
|
227
|
+
await server.emitEvent(MyEvent, (info) => info.userId === 123, { message: "hello" });
|
|
228
|
+
|
|
229
|
+
// Client: subscribe to the event
|
|
230
|
+
await client.addListener(MyEvent, { userId: 123 }, async (data) => {
|
|
231
|
+
console.log(data.message);
|
|
232
|
+
});
|
|
233
|
+
```
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"create-service-protocol.d.ts","sourceRoot":"","sources":["..\\..\\src\\protocol\\create-service-protocol.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,uBAAuB,CAAC;AACnD,OAAO,uBAAuB,CAAC;AAQ/B,OAAO,EAAmB,KAAK,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAExE;;;;;;;;GAQG;AACH,MAAM,WAAW,eAAe;IAC9B;;OAEG;IACH,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,cAAc,GAAG;QAAE,MAAM,EAAE,KAAK,EAAE,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC;IAEtF;;OAEG;IACH,MAAM,CAAC,CAAC,SAAS,cAAc,EAAE,KAAK,EAAE,KAAK,GAAG,0BAA0B,CAAC,CAAC,CAAC,CAAC;IAE9E;;;;;OAKG;IACH,OAAO,IAAI,IAAI,CAAC;CACjB;AAED;;;;;GAKG;AACH,MAAM,MAAM,0BAA0B,CAAC,QAAQ,SAAS,cAAc,IAClE;IAAE,IAAI,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,QAAQ,CAAA;CAAE,GACrD;IAAE,IAAI,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAC;IAAC,aAAa,EAAE,MAAM,CAAA;CAAE,CAAC;AAEjF;;;;;;;;GAQG;AACH,wBAAgB,qBAAqB,IAAI,eAAe,
|
|
1
|
+
{"version":3,"file":"create-service-protocol.d.ts","sourceRoot":"","sources":["..\\..\\src\\protocol\\create-service-protocol.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,uBAAuB,CAAC;AACnD,OAAO,uBAAuB,CAAC;AAQ/B,OAAO,EAAmB,KAAK,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAExE;;;;;;;;GAQG;AACH,MAAM,WAAW,eAAe;IAC9B;;OAEG;IACH,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,cAAc,GAAG;QAAE,MAAM,EAAE,KAAK,EAAE,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC;IAEtF;;OAEG;IACH,MAAM,CAAC,CAAC,SAAS,cAAc,EAAE,KAAK,EAAE,KAAK,GAAG,0BAA0B,CAAC,CAAC,CAAC,CAAC;IAE9E;;;;;OAKG;IACH,OAAO,IAAI,IAAI,CAAC;CACjB;AAED;;;;;GAKG;AACH,MAAM,MAAM,0BAA0B,CAAC,QAAQ,SAAS,cAAc,IAClE;IAAE,IAAI,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,QAAQ,CAAA;CAAE,GACrD;IAAE,IAAI,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAC;IAAC,aAAa,EAAE,MAAM,CAAA;CAAE,CAAC;AAEjF;;;;;;;;GAQG;AACH,wBAAgB,qBAAqB,IAAI,eAAe,CAqLvD"}
|
|
@@ -40,7 +40,8 @@ export function createServiceProtocol() {
|
|
|
40
40
|
headerBytes.set(uuidBytes, 0);
|
|
41
41
|
// TotalSize (16-23), Index (24-27)
|
|
42
42
|
const headerView = new DataView(headerBytes.buffer, headerBytes.byteOffset, headerBytes.byteLength);
|
|
43
|
-
headerView.
|
|
43
|
+
headerView.setUint32(16, 0, false); // 상위 4바이트 = 0 (MAX_TOTAL_SIZE < 2^32)
|
|
44
|
+
headerView.setUint32(20, header.totalSize, false); // 하위 4바이트 = totalSize
|
|
44
45
|
headerView.setUint32(24, header.index, false);
|
|
45
46
|
return bytesU.concat([headerBytes, ...(bodyBytes ? [bodyBytes] : [])]);
|
|
46
47
|
}
|
|
@@ -89,7 +90,7 @@ export function createServiceProtocol() {
|
|
|
89
90
|
const uuid = Uuid.fromBytes(uuidBytes).toString();
|
|
90
91
|
// TOTAL_SIZE, INDEX
|
|
91
92
|
const headerView = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
|
|
92
|
-
const totalSize =
|
|
93
|
+
const totalSize = headerView.getUint32(20, false); // 하위 4바이트만 읽기
|
|
93
94
|
const index = headerView.getUint32(24, false);
|
|
94
95
|
// 전체 크기 제한 확인 (우선 수행)
|
|
95
96
|
if (totalSize > PROTOCOL_CONFIG.MAX_TOTAL_SIZE) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"create-service-protocol.js","sourceRoot":"","sources":["..\\..\\src\\protocol\\create-service-protocol.ts"],"names":[],"mappings":"AACA,OAAO,uBAAuB,CAAC;AAC/B,OAAO,EACL,aAAa,EACb,KAAK,IAAI,MAAM,EACf,IAAI,EACJ,SAAS,EACT,IAAI,GACL,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,eAAe,EAAuB,MAAM,kBAAkB,CAAC;AAyCxE;;;;;;;;GAQG;AACH,MAAM,UAAU,qBAAqB;IACnC,sEAAsE;IACtE,KAAK;IACL,sEAAsE;IAEtE,MAAM,WAAW,GAAG,IAAI,SAAS,CAO/B;QACA,UAAU,EAAE,eAAe,CAAC,WAAW;QACvC,UAAU,EAAE,eAAe,CAAC,WAAW;KACxC,CAAC,CAAC;IAEH,sEAAsE;IACtE,SAAS;IACT,sEAAsE;IAEtE;;;;;;;;;;;OAWG;IACH,SAAS,WAAW,CAClB,MAIC,EACD,SAAiB;QAEjB,MAAM,WAAW,GAAG,IAAI,UAAU,CAAC,EAAE,CAAC,CAAC;QAEvC,cAAc;QACd,MAAM,SAAS,GAAG,IAAI,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,OAAO,EAAE,CAAC;QAClD,WAAW,CAAC,GAAG,CAAC,SAAS,EAAE,CAAC,CAAC,CAAC;QAE9B,mCAAmC;QACnC,MAAM,UAAU,GAAG,IAAI,QAAQ,CAC7B,WAAW,CAAC,MAAM,EAClB,WAAW,CAAC,UAAU,EACtB,WAAW,CAAC,UAAU,CACvB,CAAC;QACF,UAAU,CAAC,
|
|
1
|
+
{"version":3,"file":"create-service-protocol.js","sourceRoot":"","sources":["..\\..\\src\\protocol\\create-service-protocol.ts"],"names":[],"mappings":"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"}
|
|
@@ -11,18 +11,10 @@ export declare const PROTOCOL_CONFIG: {
|
|
|
11
11
|
/** 미완성 메시지 만료 시간 (60초) */
|
|
12
12
|
readonly EXPIRE_TIME: number;
|
|
13
13
|
};
|
|
14
|
-
export type ServiceMessage =
|
|
15
|
-
export type ServiceServerMessage =
|
|
14
|
+
export type ServiceMessage = ServiceRequestMessage | ServiceAuthMessage | ServiceProgressMessage | ServiceResponseMessage | ServiceErrorMessage | ServiceAddEventListenerMessage | ServiceRemoveEventListenerMessage | ServiceGetEventListenerInfosMessage | ServiceEmitEventMessage | ServiceEventMessage;
|
|
15
|
+
export type ServiceServerMessage = ServiceResponseMessage | ServiceErrorMessage | ServiceEventMessage;
|
|
16
16
|
export type ServiceServerRawMessage = ServiceProgressMessage | ServiceServerMessage;
|
|
17
17
|
export type ServiceClientMessage = ServiceRequestMessage | ServiceAuthMessage | ServiceAddEventListenerMessage | ServiceRemoveEventListenerMessage | ServiceGetEventListenerInfosMessage | ServiceEmitEventMessage;
|
|
18
|
-
/** 서버: 클라이언트에 리로드 명령 */
|
|
19
|
-
export interface ServiceReloadMessage {
|
|
20
|
-
name: "reload";
|
|
21
|
-
body: {
|
|
22
|
-
clientName: string | undefined;
|
|
23
|
-
changedFileSet: Set<string>;
|
|
24
|
-
};
|
|
25
|
-
}
|
|
26
18
|
/** 서버: 수신된 청크 메시지의 진행 상태 알림 */
|
|
27
19
|
export interface ServiceProgressMessage {
|
|
28
20
|
name: "progress";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"protocol.types.d.ts","sourceRoot":"","sources":["..\\..\\src\\protocol\\protocol.types.ts"],"names":[],"mappings":"AAIA,kBAAkB;AAClB,eAAO,MAAM,eAAe;IAC1B,wBAAwB;;IAExB,mBAAmB;;IAEnB,oBAAoB;;IAEpB,kBAAkB;;IAElB,0BAA0B;;CAElB,CAAC;AAMX,MAAM,MAAM,cAAc,GACtB,
|
|
1
|
+
{"version":3,"file":"protocol.types.d.ts","sourceRoot":"","sources":["..\\..\\src\\protocol\\protocol.types.ts"],"names":[],"mappings":"AAIA,kBAAkB;AAClB,eAAO,MAAM,eAAe;IAC1B,wBAAwB;;IAExB,mBAAmB;;IAEnB,oBAAoB;;IAEpB,kBAAkB;;IAElB,0BAA0B;;CAElB,CAAC;AAMX,MAAM,MAAM,cAAc,GACtB,qBAAqB,GACrB,kBAAkB,GAClB,sBAAsB,GACtB,sBAAsB,GACtB,mBAAmB,GACnB,8BAA8B,GAC9B,iCAAiC,GACjC,mCAAmC,GACnC,uBAAuB,GACvB,mBAAmB,CAAC;AAExB,MAAM,MAAM,oBAAoB,GAC5B,sBAAsB,GACtB,mBAAmB,GACnB,mBAAmB,CAAC;AAExB,MAAM,MAAM,uBAAuB,GAAG,sBAAsB,GAAG,oBAAoB,CAAC;AAEpF,MAAM,MAAM,oBAAoB,GAC5B,qBAAqB,GACrB,kBAAkB,GAClB,8BAA8B,GAC9B,iCAAiC,GACjC,mCAAmC,GACnC,uBAAuB,CAAC;AAM5B,+BAA+B;AAC/B,MAAM,WAAW,sBAAsB;IACrC,IAAI,EAAE,UAAU,CAAC;IACjB,IAAI,EAAE;QACJ,SAAS,EAAE,MAAM,CAAC;QAClB,aAAa,EAAE,MAAM,CAAC;KACvB,CAAC;CACH;AAED,gBAAgB;AAChB,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE;QACJ,IAAI,EAAE,MAAM,CAAC;QACb,OAAO,EAAE,MAAM,CAAC;QAChB,IAAI,EAAE,MAAM,CAAC;QACb,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,MAAM,CAAC,EAAE,OAAO,CAAC;QACjB,KAAK,CAAC,EAAE,OAAO,CAAC;KACjB,CAAC;CACH;AAED,oBAAoB;AACpB,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd;AAMD,wBAAwB;AACxB,MAAM,WAAW,qBAAqB;IACpC,IAAI,EAAE,GAAG,MAAM,IAAI,MAAM,EAAE,CAAC;IAC5B,IAAI,EAAE,OAAO,EAAE,CAAC;CACjB;AAED,qBAAqB;AACrB,MAAM,WAAW,sBAAsB;IACrC,IAAI,EAAE,UAAU,CAAC;IACjB,IAAI,CAAC,EAAE,OAAO,CAAC;CAChB;AAMD,wBAAwB;AACxB,MAAM,WAAW,8BAA8B;IAC7C,IAAI,EAAE,SAAS,CAAC;IAChB,IAAI,EAAE;QACJ,GAAG,EAAE,MAAM,CAAC;QACZ,IAAI,EAAE,MAAM,CAAC;QACb,IAAI,EAAE,OAAO,CAAC;KACf,CAAC;CACH;AAED,wBAAwB;AACxB,MAAM,WAAW,iCAAiC;IAChD,IAAI,EAAE,YAAY,CAAC;IACnB,IAAI,EAAE;QACJ,GAAG,EAAE,MAAM,CAAC;KACb,CAAC;CACH;AAED,8BAA8B;AAC9B,MAAM,WAAW,mCAAmC;IAClD,IAAI,EAAE,UAAU,CAAC;IACjB,IAAI,EAAE;QACJ,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;CACH;AAED,oBAAoB;AACpB,MAAM,WAAW,uBAAuB;IACtC,IAAI,EAAE,UAAU,CAAC;IACjB,IAAI,EAAE;QACJ,IAAI,EAAE,MAAM,EAAE,CAAC;QACf,IAAI,EAAE,OAAO,CAAC;KACf,CAAC;CACH;AAED,iBAAiB;AACjB,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,QAAQ,CAAC;IACf,IAAI,EAAE;QACJ,IAAI,EAAE,MAAM,EAAE,CAAC;QACf,IAAI,EAAE,OAAO,CAAC;KACf,CAAC;CACH"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@simplysm/service-common",
|
|
3
|
-
"version": "14.0.
|
|
3
|
+
"version": "14.0.4",
|
|
4
4
|
"description": "심플리즘 패키지 - 서비스 (common)",
|
|
5
5
|
"author": "심플리즘",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -17,8 +17,11 @@
|
|
|
17
17
|
"src"
|
|
18
18
|
],
|
|
19
19
|
"sideEffects": false,
|
|
20
|
+
"devDependencies": {
|
|
21
|
+
"@types/node": "^20.19.37"
|
|
22
|
+
},
|
|
20
23
|
"dependencies": {
|
|
21
|
-
"@simplysm/core-common": "14.0.
|
|
22
|
-
"@simplysm/orm-common": "14.0.
|
|
24
|
+
"@simplysm/core-common": "14.0.4",
|
|
25
|
+
"@simplysm/orm-common": "14.0.4"
|
|
23
26
|
}
|
|
24
27
|
}
|
|
@@ -110,7 +110,8 @@ export function createServiceProtocol(): ServiceProtocol {
|
|
|
110
110
|
headerBytes.byteOffset,
|
|
111
111
|
headerBytes.byteLength,
|
|
112
112
|
);
|
|
113
|
-
headerView.
|
|
113
|
+
headerView.setUint32(16, 0, false); // 상위 4바이트 = 0 (MAX_TOTAL_SIZE < 2^32)
|
|
114
|
+
headerView.setUint32(20, header.totalSize, false); // 하위 4바이트 = totalSize
|
|
114
115
|
headerView.setUint32(24, header.index, false);
|
|
115
116
|
|
|
116
117
|
return bytesU.concat([headerBytes, ...(bodyBytes ? [bodyBytes] : [])]);
|
|
@@ -174,7 +175,7 @@ export function createServiceProtocol(): ServiceProtocol {
|
|
|
174
175
|
|
|
175
176
|
// TOTAL_SIZE, INDEX
|
|
176
177
|
const headerView = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
|
|
177
|
-
const totalSize =
|
|
178
|
+
const totalSize = headerView.getUint32(20, false); // 하위 4바이트만 읽기
|
|
178
179
|
const index = headerView.getUint32(24, false);
|
|
179
180
|
|
|
180
181
|
// 전체 크기 제한 확인 (우선 수행)
|
|
@@ -21,7 +21,6 @@ export const PROTOCOL_CONFIG = {
|
|
|
21
21
|
// ----------------------------------------------------------------------
|
|
22
22
|
|
|
23
23
|
export type ServiceMessage =
|
|
24
|
-
| ServiceReloadMessage
|
|
25
24
|
| ServiceRequestMessage
|
|
26
25
|
| ServiceAuthMessage
|
|
27
26
|
| ServiceProgressMessage
|
|
@@ -34,7 +33,6 @@ export type ServiceMessage =
|
|
|
34
33
|
| ServiceEventMessage;
|
|
35
34
|
|
|
36
35
|
export type ServiceServerMessage =
|
|
37
|
-
| ServiceReloadMessage // 알림
|
|
38
36
|
| ServiceResponseMessage
|
|
39
37
|
| ServiceErrorMessage
|
|
40
38
|
| ServiceEventMessage; // 알림
|
|
@@ -53,15 +51,6 @@ export type ServiceClientMessage =
|
|
|
53
51
|
// 시스템 (공통)
|
|
54
52
|
// ----------------------------------------------------------------------
|
|
55
53
|
|
|
56
|
-
/** 서버: 클라이언트에 리로드 명령 */
|
|
57
|
-
export interface ServiceReloadMessage {
|
|
58
|
-
name: "reload";
|
|
59
|
-
body: {
|
|
60
|
-
clientName: string | undefined; // 클라이언트 이름
|
|
61
|
-
changedFileSet: Set<string>; // 변경된 파일 목록
|
|
62
|
-
};
|
|
63
|
-
}
|
|
64
|
-
|
|
65
54
|
/** 서버: 수신된 청크 메시지의 진행 상태 알림 */
|
|
66
55
|
export interface ServiceProgressMessage {
|
|
67
56
|
name: "progress";
|