TypeError: прототип объекта может быть только Object или null: undefined

Ниже, если я импортирую Entity, я получаю ошибку темы сообщения (TypeError: прототип объекта может быть только Object или null: undefined), но если я заменяю импорт фактическим объявлением Entity, код работает нормально.

Демо Stackblitz здесь.

Это Customer.ts в форме, которая выдает ошибку, когда я запускаю код с ts-node:

index.ts

export { Customer } from "./Customer";
export { Entity } from "./Entity";

Customer.ts

import { Entity } from "./index";

export class Customer extends Entity {
  sku: string;
  constructor(po: any) {
    super();
    this.sku = po.sku;
  }
}

Entity.ts

export abstract class Entity {
  id?: string;
}    

Run.ts (тестовый код)

import {Customer} from "./";

let c = new Customer({
  name: "Bob"
});
console.log(c);

Если я заменю импорт Entity таким объявлением:

export abstract class Entity {
  id?: string;
}    

export class Customer extends Entity {
  sku: string;
  constructor(po: any) {
    super();
    this.sku = po.sku;
  }
}

Затем Run.ts регистрирует это:

Customer { sku: undefined }

Другими словами, он работает нормально и не вызывает ошибок. Мысли?


person Ole    schedule 02.11.2018    source источник
comment
может быть, вы неправильно написали Entity путь? Можете ли вы указать пути?   -  person Artyom Amiryan    schedule 02.11.2018
comment
Циклический импорт, вызывающий продолжение выполнения оператора import, даже если цель еще не загружена?   -  person Matt McCutchen    schedule 02.11.2018
comment
Держи пресс! Я думаю, вы, ребята, поняли. У меня index.ts в том же корне, что и другие файлы. Я реэкспортирую все из этого файла, поэтому у меня есть центральное место для импорта. Вот что это вызывает.   -  person Ole    schedule 02.11.2018
comment
Дважды проверил. Если я импортирую Entity непосредственно из Entity.ts, проблем нет, но если я импортирую его из index.ts, возникает исключение. Я нахожу это немного странным?   -  person Ole    schedule 02.11.2018


Ответы (2)


Как я и подозревал, ваша исходная программа имеет циклический импорт. Run.ts импортирует index.ts, который импортирует Customer.ts, который снова импортирует index.ts. Поскольку index.ts уже находится в процессе загрузки и сам зависит от Customer.ts, import { Entity } from "./index"; просто связывает Entity из index.ts (который еще не установлен) с Entity из Customer.ts, и выполнение продолжается, даже если загрузка index.ts не завершена. Тогда Entity не определено в момент, когда вы пытаетесь его расширить. Вы можете возразить, что циклический импорт должен быть ошибкой или что движки JavaScript должны использовать какой-то другой алгоритм, который правильно обрабатывает ваш сценарий; Я не уполномочен комментировать, почему был выбран текущий дизайн. (Другие могут добавить информацию об этом.)

Как вы видели, изменение Customer.ts на импорт из ./Entity напрямую вместо ./index прерывает цикл, и все работает, как ожидалось. Другое решение - изменить порядок импорта в index.ts.

person Matt McCutchen    schedule 02.11.2018
comment
Замечательное наблюдение! Я сообщил об этом как об ошибке на всякий случай, если это может помочь в разработке TypeScript лучше обрабатывать / сообщать об ошибках для этого сценария. - person Ole; 02.11.2018
comment
Возможно, компилятор обнаружит циклическую зависимость и просто заменит путь ./ на ./Entity. Они эквивалентны, и поскольку это код времени выполнения, все довольны ... - person Ole; 02.11.2018

Вы можете попробовать эту команду и проверить приложение:

  1. ng update @angular/cli @angular/core --force
  2. npm install
  3. ng serve -o
person Kaushik Vaghani    schedule 14.09.2019