Stworzyłem usługę SocketService, w zasadzie inicjalizuje gniazdo, aby aplikacja nasłuchiwała na porcie. Ta usługa współdziała również z niektórymi komponentami.
// socket.service.ts
export class SocketService {
constructor() {
// Initializes the socket
}
...
}
Wiem, że kod w konstruktorze SocketService () zaczyna działać tylko wtedy, gdy składnik używa SocketService.
Zwykle kod w app.ts wygląda tak:
// app.ts
import {SocketService} from './socket.service';
...
class App {
constructor () {}
}
bootstrap(App, [SocketService]);
Jednak chcę, aby ta usługa działała podczas uruchamiania aplikacji. Zrobiłem więc sztuczkę, po prostu private _socketService: SocketService
dodałem konstruktor aplikacji (). Więc teraz kody wyglądają tak:
// app.ts (nowy)
import {SocketService} from './socket.service';
...
class App {
constructor (private _socketService: SocketService) {}
}
bootstrap(App, [SocketService]);
Teraz działa. Problem polega na tym, że czasami kody w konstruktorze () SocketService działają, czasami nie. Jak więc mam to zrobić poprawnie? Dzięki
typescript
angular
Hongbo Miao
źródło
źródło
Odpowiedzi:
Odpowiedź Stuarta wskazuje we właściwym kierunku, ale nie jest łatwo znaleźć informacje w APP_INITIALIZER. Krótka wersja polega na tym, że można go użyć do uruchomienia kodu inicjującego przed uruchomieniem jakiegokolwiek innego kodu aplikacji. Szukałem przez chwilę i znalazłem wyjaśnienia tutaj i tutaj , które podsumuję na wypadek, gdyby zniknęły z sieci.
APP_INITIALIZER jest zdefiniowany w angular / core. Umieszczasz go w swoim app.module.ts w ten sposób.
import { APP_INITIALIZER } from '@angular/core';
APP_INITIALIZER to OpaqueToken (lub InjectionToken od Angular 4), który odwołuje się do usługi ApplicationInitStatus. ApplicationInitStatus to wielu dostawców . Obsługuje wiele zależności i możesz go wielokrotnie używać na liście dostawców. Jest używany w ten sposób.
@NgModule({ providers: [ DictionaryService, { provide: APP_INITIALIZER, useFactory: (ds: DictionaryService) => () => return ds.load(), deps: [DictionaryService], multi: true }] }) export class AppModule { }
Ta deklaracja dostawcy nakazuje klasie ApplicationInitStatus uruchomienie metody DictionaryService.load (). load () zwraca obietnicę, a ApplicationInitStatus blokuje uruchamianie aplikacji, dopóki obietnica nie zostanie rozwiązana. Funkcja load () jest zdefiniowana w ten sposób.
load(): Promise<any> { return this.dataService.getDiscardReasons() .toPromise() .then( data => { this.dictionaries.set("DISCARD_REASONS",data); } ) }
Skonfiguruj w ten sposób, że słownik jest ładowany jako pierwszy, a inne części aplikacji mogą bezpiecznie na nim polegać.
Edycja: należy pamiętać, że spowoduje to wydłużenie czasu wczytywania aplikacji z góry o tyle, ile zajmie metoda load (). Jeśli chcesz tego uniknąć, możesz zamiast tego użyć resolvera na trasie.
źródło
init
metody. Chociaż konstruktorzy rzeczywiście powinni być tak proste, jak to tylko możliwe, sama ta myśl nie sprawia, że jest to właściwe rozwiązanie. UżywanieAPP_INITIALIZER
nie.SocketService
Zamiast tego przenieś logikę w konstruktorze do metody, a następnie wywołaj ją w konstruktorze lubngOnInit
SocketService
export class SocketService{ init(){ // Startup logic here } }
Aplikacja
import {SocketService} from './socket.service'; ... class App { constructor (private _socketService: SocketService) { _socketService.init(); } } bootstrap(App, [SocketService]);
źródło
Promise
ze swojejinit()
metody, a następnie łańcuch w razie potrzeby. W każdym przypadku można to zrobić, ale prawdopodobnie będzie to trudne i ustalenie szczegółów będzie zależało od Ciebie. Jeśli potrzebujesz dalszej pomocy, zawsze możesz zadać pytanie zawierające szczegółowe informacje o Twoim problemie, a społeczność z przyjemnością Ci pomoże.Zobacz także APP_INITIALIZER , opisaną jako;
źródło
Spróbuj utworzyć konstruktora usługi, a następnie wywołaj go w ngOnInit () swojego komponentu.
export class SocketService { constructor() { } getData() { //your code Logic } }
export class AppComponent { public record; constructor(private SocketService: DataService){ } ngOnInit() { this.SocketService.getData() .subscribe((data:any[]) => { this.record = data; }); } }
Mam nadzieję że to pomoże.
źródło