Angular 5プロジェクトに、いくつかの構成状態を保持するサービスがあります。
@Injectable
export class FooService {
isIncognito: boolean = null;
constructor() {
// I want Angular to wait for this to resolve (i.e. until `isIncognito != null`):
FooService.isIncognitoWindow()
.then( isIncognito => {
this.isIncognito= isIncognito;
} );
}
private static isIncognitoWindow(): Promise<boolean> {
// https://stackoverflow.com/questions/2909367/can-you-determine-if-chrome-is-in-incognito-mode-via-a-script
// https://developer.mozilla.org/en-US/docs/Web/API/LocalFileSystem
return new Promise<boolean>( ( resolve, reject ) => {
let rfs = window['requestFileSystem'] || window['webkitRequestFileSystem'];
if( !rfs ) {
console.warn( "window.RequestFileSystem not found." );
resolve( false );
}
const typeTemporary = 0;
const typePersistent = 1;
// requestFileSystem's callbacks are made asynchronously, so we need to use a promise.
rfs(
/*type: */ typeTemporary,
/* bytesRequested: */ 100,
/* successCallback: */ function( fso: WebKitFileSystem ) {
resolve( false );
},
/* errorCallback: */ function( err: any /* FileError */ ) {
resolve( true );
}
);
} );
}
}
このサービスは、私のプロジェクトの多くのコンポーネントで使用されており、コンストラクター引数として渡されます。例えば:
@Component( {
moduleId: module.id,
templateUrl: 'auth.component.html'
} )
export class AuthComponent implements OnInit {
constructor( private fooService: FooService ) {
}
ngOnInit(): void {
// do stuff that depends on `this.fooService.isIncognito != null`
}
}
理想的には、Angularが他のコンポーネントFooService::isIncognitoWindow()
にを注入する前に、最初に約束が解決されるのを待って(解決は即座に行われますが、同期は行われません)したいと思いFooService
ます。
別の解決策はFooComponent.isIncognito
、のプロパティをに変更し、Promise<boolean>
それを再度解決しngOnInit
て、コールバックを介して残りを呼び出すことですが、これは、すべてのコンポーネントがPromiseのメイン関数を再度呼び出すことを意味します-つまり、バッファリングされたObservableまたは代わりに主題、そしてそれは不必要に複雑になっています-すべて単一のboolean
値のために。また、私が行う必要のない多くのコードをリファクタリングすることも意味します。
できることは、APP_INITIALIZER
トークンを使用してFooService
、アプリケーションが起動する前にが初期化されていることを確認することです。以下のコードでは、angularはload
メソッドによって返されたpromiseが解決されたときにのみアプリケーションを開始します。
FooService.ts
@Injectable()
export class FooService {
isIncognito: boolean = null;
public load()// <=== the method to be called and waited on during initialiation
{
return FooService.isIncognitoWindow().then(isIncognito =>
{
this.isIncognito = isIncognito;
});
}
private static isIncognitoWindow(): Promise<boolean> {
{ //your method here
app.module.ts
export function loadFooService(fooService: FooService): Function
{
return () => { return fooService.load() };
}
@NgModule({
imports: [ BrowserModule, FormsModule ],
declarations: [ AppComponent, HelloComponent ],
bootstrap: [ AppComponent ],
providers: [ FooService,
{ provide: APP_INITIALIZER, useFactory:loadFooService , deps: [FooService], multi: true },]
})
stackblitzの例を参照してください
この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。
侵害の場合は、連絡してください[email protected]
コメントを追加