From c011352a3f3d9a1bb70585a5e25bfba99320919f Mon Sep 17 00:00:00 2001 From: Craig Harshbarger Date: Mon, 18 Aug 2025 21:19:01 -0500 Subject: [PATCH 1/2] Add a count method --- src/createEmitter.ts | 21 +++++++++++++++++++++ tests/events.spec-d.ts | 29 +++++++++++++++++++++++++++++ tests/events.spec.ts | 18 ++++++++++++++++++ 3 files changed, 68 insertions(+) diff --git a/src/createEmitter.ts b/src/createEmitter.ts index b606740..583495c 100644 --- a/src/createEmitter.ts +++ b/src/createEmitter.ts @@ -149,6 +149,26 @@ export function createEmitter(options?: EmitterOp onEvent(event, payload!) } + type CountOptions = { + global?: boolean + } + + function count(): number + function count(event: E, options?: CountOptions): number + function count(event?: E, { global = false }: CountOptions = {}): number { + if(event) { + const eventHandlers = handlers.get(event)?.size ?? 0 + + if(global) { + return eventHandlers + globalHandlers.size + } + + return eventHandlers + } + + return globalHandlers.size + } + function clear(): void { handlers.clear() globalHandlers.clear() @@ -210,6 +230,7 @@ export function createEmitter(options?: EmitterOp next, emit, clear, + count, setOptions, } } diff --git a/tests/events.spec-d.ts b/tests/events.spec-d.ts index 7388f55..0565dd2 100644 --- a/tests/events.spec-d.ts +++ b/tests/events.spec-d.ts @@ -198,3 +198,32 @@ describe('emitter.setOptions', () => { expectTypeOf().toEqualTypeOf() }) }) + +describe('emitter.count', () => { + test('has the correct return type', () => { + const emitter = createEmitter() + const response = emitter.count() + + type Source = typeof response + type Expected = number + + expectTypeOf().toEqualTypeOf() + }) + + test('accepts only valid event names', () => { + const emitter = createEmitter() + + emitter.count('ping') + emitter.count('hello') + emitter.count('user') + + // @ts-expect-error - Invalid event name + emitter.count('invalid') + }) + + test('accepts a global option', () => { + const emitter = createEmitter() + + emitter.count('ping', { global: true }) + }) +}) diff --git a/tests/events.spec.ts b/tests/events.spec.ts index bd80122..308659e 100644 --- a/tests/events.spec.ts +++ b/tests/events.spec.ts @@ -372,4 +372,22 @@ test('next without event returns the global event payload', async () => { kind: 'hello', payload: 'world', }) +}) + +describe('emitter.count', () => { + test('returns the correct number of handlers', () => { + const emitter = createEmitter<{ hello: void, goodbye: void }>() + + emitter.on('hello', vi.fn()) + emitter.on('goodbye', vi.fn()) + emitter.on(vi.fn()) + + expect(emitter.count()).toBe(1) + expect(emitter.count('hello')).toBe(1) + expect(emitter.count('goodbye')).toBe(1) + expect(emitter.count('hello', { global: true })).toBe(2) + expect(emitter.count('goodbye', { global: true })).toBe(2) + expect(emitter.count('hello', { global: false })).toBe(1) + expect(emitter.count('goodbye', { global: false })).toBe(1) + }) }) \ No newline at end of file From 52c366a790b542ce8c766822c9412e513cef5c33 Mon Sep 17 00:00:00 2001 From: Craig Harshbarger Date: Mon, 18 Aug 2025 21:20:37 -0500 Subject: [PATCH 2/2] Add method to docs --- docs/index.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/index.md b/docs/index.md index c3bd1bd..b87301a 100644 --- a/docs/index.md +++ b/docs/index.md @@ -19,7 +19,7 @@ features: - title: Type safety details: Type safe events and payload - title: Useful API - details: Includes on, off, once, next, emit, and clear + details: Includes on, off, once, next, emit, count, and clear - title: Support Global Handlers details: Setup handlers that run on all events ---