Skip to content

Commit 61cb650

Browse files
author
Your Name
committed
Fix #5448: Bug: [5.25.0] typing issue when using assertEvent and generi
1 parent e176216 commit 61cb650

File tree

4 files changed

+67
-2
lines changed

4 files changed

+67
-2
lines changed

packages/core/src/assert.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ import { matchesEventDescriptor, toArray } from './utils.ts';
2626
*/
2727
export function assertEvent<
2828
TEvent extends EventObject,
29-
TAssertedDescriptor extends EventDescriptor<TEvent>
29+
TAssertedDescriptor extends string = string
3030
>(
3131
event: TEvent,
3232
type: TAssertedDescriptor | readonly TAssertedDescriptor[]

packages/core/test/assert.test.ts

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { createActor, createMachine, assertEvent } from '../src';
1+
import { createActor, createMachine, assertEvent, InspectionEvent } from '../src';
22

33
describe('assertion helpers', () => {
44
it('assertEvent asserts the correct event type', () => {
@@ -103,4 +103,23 @@ describe('assertion helpers', () => {
103103

104104
return promise;
105105
});
106+
107+
it('assertEvent works with generics', () => {
108+
// Test with InspectionEvent and generic type parameter
109+
function test<TEVENT extends InspectionEvent>(event: TEVENT) {
110+
assertEvent(event, '@xstate.event');
111+
event.event satisfies any;
112+
}
113+
114+
// This should compile without errors
115+
const mockEvent: InspectionEvent = {
116+
type: '@xstate.event',
117+
rootId: 'root',
118+
actorRef: { id: '1' } as any,
119+
sourceRef: undefined,
120+
event: { type: 'test' }
121+
};
122+
123+
expect(() => test(mockEvent as any)).not.toThrow();
124+
});
106125
});
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
import { assertEvent, InspectionEvent } from '../src/index';
2+
3+
describe('assertEvent type tests', () => {
4+
it('should work with non-generic event types', () => {
5+
function test(event: InspectionEvent) {
6+
assertEvent(event, '@xstate.event');
7+
event.event satisfies any;
8+
}
9+
});
10+
11+
it('should work with generic event types', () => {
12+
function test<TEVENT extends InspectionEvent>(event: TEVENT) {
13+
assertEvent(event, '@xstate.event');
14+
event.event satisfies any;
15+
}
16+
});
17+
18+
it('should work with generic event types and multiple descriptors', () => {
19+
function test<TEVENT extends InspectionEvent>(event: TEVENT) {
20+
assertEvent(event, ['@xstate.event', '@xstate.snapshot']);
21+
event.event satisfies any;
22+
}
23+
});
24+
25+
it('should properly narrow types after assertion', () => {
26+
type MyEvent = { type: 'foo'; value: string } | { type: 'bar'; count: number };
27+
28+
function test<T extends MyEvent>(event: T) {
29+
assertEvent(event, 'foo');
30+
event.value satisfies string;
31+
// @ts-expect-error
32+
event.count;
33+
}
34+
});
35+
});

test_generics.ts

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
import { InspectionEvent, assertEvent } from './packages/core/src/index.ts';
2+
3+
function test(event: InspectionEvent) {
4+
assertEvent(event, '@xstate.event');
5+
console.log(event.event);
6+
}
7+
8+
function test2<TEVENT extends InspectionEvent>(event: TEVENT) {
9+
assertEvent(event, '@xstate.event');
10+
console.log(event.event);
11+
}

0 commit comments

Comments
 (0)