feat(sdk): P2.6 @insignia/iios-message-web (React hooks) + allowlist boundary
MessageProvider/useThread/useMessages over the kernel-client socket (live append, typing, dedupe). Reconnect test (re-opens active thread). Rewrote import-boundary as an allowlist so SDK<->service sibling imports are forbidden both ways. 28 tests. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,51 @@
|
||||
import { describe, it, expect } from 'vitest';
|
||||
import { MessageSocket } from './message-socket';
|
||||
import type { SocketLike } from './types';
|
||||
|
||||
class FakeSocket implements SocketLike {
|
||||
handlers = new Map<string, Array<(...a: unknown[]) => void>>();
|
||||
acks: Array<{ event: string; payload: unknown }> = [];
|
||||
ackReturn: unknown = { threadId: 't5', status: 'OPEN', history: [] };
|
||||
|
||||
on(event: string, handler: (...a: unknown[]) => void): unknown {
|
||||
const list = this.handlers.get(event) ?? [];
|
||||
list.push(handler);
|
||||
this.handlers.set(event, list);
|
||||
return this;
|
||||
}
|
||||
off(): unknown {
|
||||
return this;
|
||||
}
|
||||
emit(): unknown {
|
||||
return this;
|
||||
}
|
||||
async emitWithAck(event: string, ...args: unknown[]): Promise<unknown> {
|
||||
this.acks.push({ event, payload: args[0] });
|
||||
return this.ackReturn;
|
||||
}
|
||||
connect(): unknown {
|
||||
return this;
|
||||
}
|
||||
disconnect(): unknown {
|
||||
return this;
|
||||
}
|
||||
trigger(event: string, ...args: unknown[]): void {
|
||||
(this.handlers.get(event) ?? []).forEach((h) => h(...args));
|
||||
}
|
||||
}
|
||||
|
||||
describe('MessageSocket reconnect resilience', () => {
|
||||
it('re-opens the active thread when the socket reconnects (no lost subscription)', async () => {
|
||||
const fake = new FakeSocket();
|
||||
const ms = new MessageSocket({ serviceUrl: 'http://localhost:3200', token: 'tok' }, fake);
|
||||
|
||||
await ms.openThread('t5');
|
||||
const before = fake.acks.filter((a) => a.event === 'open_thread').length;
|
||||
|
||||
fake.trigger('connect'); // simulate a reconnect
|
||||
|
||||
const opens = fake.acks.filter((a) => a.event === 'open_thread');
|
||||
expect(opens.length).toBe(before + 1);
|
||||
expect(opens.at(-1)?.payload).toMatchObject({ threadId: 't5' });
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user