2017-06-28 11 views
26

Używaliśmy TypeScript 2.2. Po aktualizacji do 2.4, możemy teraz uzyskać to na kompilacji:Po uaktualnieniu TypeScript, rejestracja kontrolera Angular nie kompiluje się teraz

błąd TS2345: argument typu 'typeof TopMenuController' nie jest przypisane do parametru typu 'iniekcyjne <IControllerConstructor>'. Typ 'typeof TopMenuController' nie można przypisać do '(string | (new (... args: any []) = > IController) | ((... args: any []) = > void | IController)) [] ". Brak właściwości "push" w typie "typeof TopMenuController".

ts \ controllers \ TopMenuController.ts (2,18): błąd TS2559: Typ "TopMenuController" nie ma wspólnych cech z typem "IController".

Nie rozumiem pierwszego błędu i Googling było trudne. Proszę tylko o pomoc przy pierwszym błędzie. (Otrzymuję drugi błąd z powodu moich prób rozwiązania pierwszego). Oto kontroler:

export class TopMenuController implements angular.IController { 
    static $inject = ["$templateCache", "Restangular"]; 

    constructor(
     private readonly $templateCache: angular.ITemplateCacheService, 
     private readonly restangular: Restangular.IElement) { 
    } 
} 

I tak się rejestruje.

Jak zmodyfikować moją definicję kontrolera lub jego rejestrację, aby nasz kod znów się kompilował?

(Wyjmowanie implements angular.IController nieco usuwa drugi błąd, ale pierwsze szczątki)

Edit: znalazłem this bug

Odpowiedz

27

ponieważ wszystkie właściwości IController są opcjonalne, wierzę błędów jesteś widzenie jest wynikiem nowego sprawdzenia "słabych typów" w TypeScript 2.4. Aby uzyskać szczegółowe informacje, sprawdź numer this link from Microsoft. Sprawdź także this related Github issue.

Niektóre odpowiednie cytaty z Microsoft:

W maszynopisie 2.4, dodajemy podobną czek na co nazywamy słabych typy. Dowolny typ zawierający tylko opcjonalne właściwości jest uważany za słaby typ , ponieważ zapewnia on niewiele ograniczeń co do tego, co można przypisać do niego .

...

W maszynopisie 2.4, to teraz błąd przypisać nic do słabego typu gdy nie ma nakładania się właściwości.

...

Można myśleć o tym jako maszynopis „zaostrza się” słabe gwarancje tych typów złapać co inaczej byłoby silent błędów.

Ponieważ jest to łamanie zmiana, być może trzeba wiedzieć o obejścia, które są takie same jak dla surowych obiektów dosłownych kontroli:

  1. stwierdzenie właściwości, jeśli naprawdę nie istnieją.
  2. Dodaj sygnaturę indeksu do słabego typu (np. [PropName: ciąg]: {}).
  3. Użyj asercji typu (tj. Opts jako Opcje).

Edit: Na podstawie tych informacji, to proste rozwiązanie byłoby wtedy wdrożyć jedną z metod określonych w IController. Na przykład, jak wspomniano przez @Amy w komentarzach, można po prostu zdefiniować pustą metodę $onInit w kontrolerze.

Edit: Dla kompletności, oto pełny kod:

export class TopMenuController implements angular.IController { 
    static $inject = ["$templateCache", "Restangular"]; 

    $onInit() { } 

    constructor(
     private readonly $templateCache: angular.ITemplateCacheService, 
     private readonly restangular: Restangular.IElement) { 
    } 
} 
+4

można poprawnie zidentyfikować problem. Dodanie '$ onInit =() => {};' do mojego kontrolera sprawiło, że wszystkie moje problemy zniknęły. – Amy

+0

Czy możesz zaktualizować odpowiedź za pomocą rozwiązania? Gdzie powinienem umieścić $ onInit =() => {}; –

+0

@FrankModica Tnx! –

3

również w obliczu tego samego problemu, który mam rozwiązane przez

  • realizacji IController

  • dodaj ten kod przed konstruktorem $onInit =() => { };

tutaj jest pełny kod nadzieję, że to da jasny obraz

module MyApp { 
    export class HomeController implements angular.IController { 
     $onInit =() => { }; 
     user: string; 
     constructor() { 
      this.user = "mali"; 
     } 
    } 
    angular.module('app').controller('homeController', MyApp.HomeController) 
} 

Szczęśliwy kodowania

+0

Czy nie jest to rozwiązanie sugerowane w innej odpowiedzi? –

+1

Tak, rzeczywiście. Ale dla początkującego użytkownika, takiego jak ja, trochę trudno było zrozumieć, gdzie zatrzymać $ onInit =() => {}; dlatego opublikowałem pełny kod dla lepszego zrozumienia. Możesz zobaczyć w komentarzach także osoby pytające, gdzie je umieścić. – UniCoder

+0

Mam to, dziękuję. Zaktualizowałem swoją odpowiedź na kod PO. Nawiasem mówiąc, nie jestem pewien, czy miałeś na myśli sugerować, że '$ onInit' musi nadejść przed konstruktorem, ale może być w dowolnym miejscu kontrolera. –

Powiązane problemy