Upgrade to Pro — share decks privately, control downloads, hide ads and more …

npm-Packages for Angular

npm-Packages for Angular

Session from my talk at BASTA! 2017 in Mainz (Germany).

Manfred Steyer

September 26, 2017
Tweet

More Decks by Manfred Steyer

Other Decks in Programming

Transcript

  1. Über mich … • Manfred Steyer • SOFTWAREarchitekt.at • Trainer

    & Consultant • Focus: Angular • Google Developer Expert (GDE) Page ▪ 2 Manfred Steyer
  2. Inhalt • npm-Pakete • Barrels • Projektstart • Test &

    Deployment • DEMO • Plugin Systeme
  3. package.json { "name": "lib-starter", "description": "...", "version": "0.0.2", "main": "bundles/lib-starter.umd.js",

    "module": "index.es5.js", "es2015": "index.js" } EcmaScript 5 als UMD-Bundle EcmaScript 5 mit Modulen (import, export) EcmaScript 2015
  4. package.json { "name": "lib-starter", "description": "...", "version": "0.0.2", "main": "bundles/lib-starter.umd.js",

    "module": "index.es5.js", "es2015": "index.js" } import { … } from 'lib-starter'; import { … } from 'libstarter/other-file';
  5. Barrels • ES Module: Datei == Modul • Zu feingranular

    für Konsumenten der Bibliothek • Barrels fassen verschiedene Exporte aus den einzelnen Dateien zusammen • "Public API" • Standard-Barrel: Entry Point • Weitere Barrels möglich
  6. index.ts als Barrel export * from './src/demo.service'; export { OtherDemoService

    } from './src/other-demo.service'; @NgModule({ … }) export class LibStarterModule { }
  7. Metadaten für AOT Bibliothek muss für AOT Metadaten bereitstellen {

    […] "angularCompilerOptions": { "strictMetadataEmit": true, "skipTemplateCodegen": true } }
  8. Generator • npm install -g yo • npm install -g

    generator-angular2-library • yo angular2-library
  9. Pakete lokal testen • Symbolische Links • Bibliothek: npm link

    • Konsument: npm link name-der-bibliothek
  10. Lessons Learned • Zum Debuggen src-Ordner linken • Ggf. src-Ordner

    sogar kopieren • ng serve --preserve-symlinks • Für Test vor Production: dist-Ordner linken + AOT
  11. Lokale npm-Registry • TFS • Nexus • Verdaccio • Leichtgewichtiges

    Node-Paket • Installation: npm i -g verdaccio • Start: verdaccio
  12. Alternativen zur Auswahl der Registry • Global: npm set registry

    http://localhost:4873 • Standard: registry.npmjs.org • npm get registry • Pro Projekt: .npmrc im Projektroot
  13. Regel #1 • Tun Sie es nicht! :-) • Das

    Angular und das Tooling funktionieren am besten, wenn alles gemeinsam kompiliert wird (Angular CLI oder WebPack, Tree Shaking) • Angular selbst es an und für sich egal, wie Module geladen werden … • Versuchen mit Paketen und einer npm-Registry zu arbeiten • Häufig gibt es eine endliche Liste an Plugins …
  14. Und wenn ich unbedingt möchte? • Wechseln Sie zu SystemJS

    • Angular CLI/ WebPack gehen davon aus, dass alles zusammen kompiliert wird • Seed: https://github.com/mgechev/angular-seed • Vergessen Sie Tree Shaking • Nutzen Sie Lazy Loading ODER • Laden Sie Angular Module manuell
  15. Lazy Loading const ROUTES: Routes = [ { path: 'home',

    component: HomeComponent, }, { path: 'lazy', loadChildren: './lazy/lazy.module#LazyModule' } ]
  16. Lazy Loading const ROUTES: Routes = [ { path: 'home',

    component: HomeComponent, }, { path: 'lazy', loadChildren: () => System.import('http://127.0.0.1:8080/plugin-rollup.umd.js') .then(m => m.SampleModule) } ]
  17. Umsetzung @Component({ … }) export class AppComponent implements AfterViewInit, OnDestroy

    { […] @ViewChild("placeholder", {read: ViewContainerRef}) viewContainer: ViewContainerRef; […] }
  18. Umsetzung @Component({ … }) export class AppComponent implements AfterViewInit, OnDestroy

    { […] @ViewChild("placeholder", {read: ViewContainerRef}) viewContainer: ViewContainerRef; componentRef: ComponentRef<{}>; […] }
  19. Umsetzung @Component({ … }) export class AppComponent implements AfterViewInit, OnDestroy

    { constructor(private loader: NgModuleFactoryLoader, private injector: Injector) { } @ViewChild("placeholder", {read: ViewContainerRef}) viewContainer: ViewContainerRef; componentRef: ComponentRef<{}>; […] }
  20. ngAfterViewInit() { this.loader.load('http://127.0.0.1:8080/plugin-rollup.umd.js#SampleModule') .then((moduleFactory) => { let moduleRef = moduleFactory.create(this.injector);

    let module = moduleRef.instance; let compType = module.constructor.decorators[0].args[0].exports .find( e => e.name == 'DashBoardComponent'); […] }); }
  21. ngAfterViewInit() { this.loader.load('http://127.0.0.1:8080/plugin-rollup.umd.js#SampleModule') .then((moduleFactory) => { let moduleRef = moduleFactory.create(this.injector);

    let module = moduleRef.instance; let compType = module.constructor.decorators[0].args[0].exports .find( e => e.name == 'DashBoardComponent'); let componentFactoryResolver = moduleRef.componentFactoryResolver; let componentFactory = componentFactoryResolver .resolveComponentFactory(compType); […] }); }
  22. ngAfterViewInit() { this.loader.load('http://127.0.0.1:8080/plugin-rollup.umd.js#SampleModule') .then((moduleFactory) => { let moduleRef = moduleFactory.create(this.injector);

    let module = moduleRef.instance; let compType = module.constructor.decorators[0].args[0].exports .find( e => e.name == 'DashBoardComponent'); let componentFactoryResolver = moduleRef.componentFactoryResolver; let componentFactory = componentFactoryResolver .resolveComponentFactory(compType); let componentRef = this.viewContainer .createComponent(componentFactory, null, this.injector); […] }); }
  23. ngAfterViewInit() { this.loader.load('http://127.0.0.1:8080/plugin-rollup.umd.js#SampleModule') .then((moduleFactory) => { let moduleRef = moduleFactory.create(this.injector);

    let module = moduleRef.instance; let compType = module.constructor.decorators[0].args[0].exports .find( e => e.name == 'DashBoardComponent'); let componentFactoryResolver = moduleRef.componentFactoryResolver; let componentFactory = componentFactoryResolver .resolveComponentFactory(compType); let componentRef = this.viewContainer .createComponent(componentFactory, null, this.injector); let comp: any = componentRef.instance; this.componentRef = componentRef; }); }
  24. Fazit Pakete für Struktur und Reuse Angular Package Format Yeoman-

    Generator npm link Eigene Registry Plugins als Ultima Ratio