Skip to content

More strictly typed events #4808

Closed
Closed
@ReneWerner87

Description

@ReneWerner87

hi and thx for this @MaximeKjaer
#3822

Observation

I wanted to use socketio together with rxjs and found out that the typescript compiler can no longer follow through the type EventEmitter
https://github.com/socketio/socket.io/blame/fd9dd74eeed3fa6a15c63240df30cc3b7357102f/lib/typed-events.ts#L93
https://github.com/ReactiveX/rxjs/blob/master/src/internal/observable/fromEvent.ts#L62-L110

example code which i have reduced to the essential(click me)
import { fromEvent } from 'rxjs';
import { EventEmitter } from 'events';

interface EventsMap {
    [event: string]: any;
}
declare type EventNames<Map extends EventsMap> = keyof Map & (string | symbol);

// here the event emitter causes problems
class MyTarget<UserEvents extends EventsMap> extends EventEmitter {
// since the eventemitter adds the general event listening ("addListener", "removeListener") methods without strict types
    on<Ev extends EventNames<UserEvents>>(ev: Ev, listener: UserEvents[Ev]) {
        return this;
    }
    off<Ev extends EventNames<UserEvents>>(ev: Ev, listener: UserEvents[Ev]) {
        return this;
    }
}

// socket io event declaration approach - @see https://socket.io/docs/v4/typescript/
interface MyEvents {
    foo: (firstParam: boolean) => void;
}

const target = new MyTarget<MyEvents>();

// expect boolean type for the argument
fromEvent(target, 'foo').subscribe((firstParam) => {
    console.log('firstParam', firstParam);
});

Problem

Since the eventemitter adds the general event listening ("addListener", "removeListener") methods without strict types, the typescript compiler cannot follow the listener argument types

with EventEmitter
image

without EventEmitter
image

same also happens with the direct usage of addListener and removeListener
in example https://socket.io/docs/v4/typescript/#types-for-the-server

socket.addListener('basicEmit', (a, b, c) => {})

Idea

The request would be to get rid of the native EventEmitter and replace it with the methods with a stricter one
so that also the typescript of other libraries can follow and more type support for the other native methods exists

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions