Расширяется от обобщенного параметра c в Typescript - PullRequest
1 голос
/ 25 марта 2020

Я пытаюсь динамически расширить класс. При создании этого класса я хотел бы указать класс, который он выводит, а не по определению.

Зачем мне это нужно: у меня есть интерфейс, содержащий тысячи полей. Я автоматически генерирую классы реализации этого интерфейса в зависимости от необходимости (один может вернуть undefined для члена поля, другой вызовет исключение).

Мне нужен конкретный класс, который будет расширять этот класс в общем c виде:

// This interface is automatically generated
interface AbstractData {
    field?: string;
    // thousands of other fields.
}

// This class is automatically generated
class BaseData implements AbstractData {
    field?: string;
    // thousands of other fields.
}

// This class is automatically generated
class CheckedData implements AbstractData {
    private underlying_field?: string;
    public get field(): string {
        if (this.underlying_field === undefined) {
            throw new Error('field is undefined');
        }
        return this.underlying_field;
    }
    public set field(v: string) { this.underlying_field = v; }
    // thousands of other accessors.
}

class ConcreteData<T> extends T { // Can't do this
    public constructor(data: AbstractData) {
        Object.setPrototypeOf(this, data);
    }

    public get additionalField() { return `field: ${this.field}`; }
}

const data = { field: 'value' };
const b = new ConcreteData<BaseData>(data);
console.log(b.field, b.additionalField);

В одном и том же ключе есть несколько вопросов, но, похоже, нет ответа, отвечающего моим потребностям:

Последний раз заставил меня почесать голову, но он не подходит. «Промежуточный» класс не указывается при создании экземпляра, он все равно потребует написания специальных версий ConcreteData для каждой специализации интерфейса. Это означает, что если вы добавите третий способ доступа к данным, вам потребуется третья специализация для ConcreteData. Но я намерен иметь много различных типов ConcreteData -подобных классов против AbstractData, что делает это решение непрактичным.

Есть ли способ заставить класс наследоваться от другого класса на основе параметров, предоставленных при создании экземпляра и все еще сохраняете преимущества системы набора Typescript?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...