Answer the question
In order to leave comments, you need to log in
How to organize lazy loading of external scripts in Angular 2+ (CLI)?
There was a need to load a large library to generate pdf on the frontend (over 1Mb).
The library itself is for nodejs, but there is a compiled version for the browser (browserify)
If everything is clear with modules and lazy, then the off-documentation says to load such scripts in the scripts block of the .angular-cli config, while they are loaded into the scripts bundle
I want to load this library only when needed, and unload it from memory when finished.
Is there any elegant solution to the problem?
PS With advice about server-side generation, please pass by, the task is to generate on the client.
Answer the question
In order to leave comments, you need to log in
I decided this way: I
wrote a service loader for scripts:
import { Injectable } from '@angular/core';
import { Observable } from 'rxjs/Observable';
import { Observer } from 'rxjs/Observer';
@Injectable()
export class ScriptLoaderService {
private scripts: ScriptModel [] = [];
public load(script: ScriptModel): Observable<ScriptModel> {
return new Observable<ScriptModel>((observer: Observer<ScriptModel>) => {
const existingScript = this.scripts.find(s => s.name === script.name);
// Complete if already loaded
if (existingScript && existingScript.loaded) {
observer.next(existingScript);
observer.complete();
} else {
// Add the script
this.scripts = [...this.scripts, script];
// Load the script
const scriptElement = document.createElement('script');
scriptElement.type = 'text/javascript';
scriptElement.src = script.src;
scriptElement.onload = () => {
script.loaded = true;
observer.next(script);
observer.complete();
};
scriptElement.onerror = (error: any) => {
observer.error('Couldn\'t load script ' + script.src);
};
document.getElementsByTagName('body')[0].appendChild(scriptElement);
}
});
}
}
export interface ScriptModel {
name: string;
src: string;
loaded: boolean;
}
Didn't find what you were looking for?
Ask your questionAsk a Question
731 491 924 answers to any question