Angular a Aurelia, potomkovia starého dobrého JavaScriptu Angular 1, sú divokí konkurenti, vyvíjaní a vydávaní približne v rovnakom čase a s podobnou filozofiou, odlišujú sa však mnohými kľúčovými spôsobmi. V tomto článku podrobne porovnáme tieto rozdiely vo funkciách a kóde.
Dlhý príbeh, Aureliu vytvoril Rob Eisenberg, známy ako tvorca Durandala a Caliburna. Pracoval na tíme Angular 2 v spoločnosti Google, ale odišiel v roku 2014, keď sa jeho názory na to, ako by mal vyzerať moderný rámec, líšili od tých ich.
Podobnosti pretrvávajú aj na technickejšej úrovni: Šablóny a komponenty (alebo vlastné prvky), ktoré sú s nimi spojené, sú jadrom aplikácií Angular aj Aurelia a obe vyžadujú, aby ste mali koreňový komponent (t. J. Aplikáciu). Ďalej Angular aj Aurelia vo veľkej miere používajú dekorátory na konfiguráciu komponentov. Každý komponent má pevný životný cyklus, do ktorého sa môžeme zapojiť.
Kľúčový rozdiel je podľa Roba Eisenberga v kóde: Aurelia je nenápadná. Pri vývoji aplikácie Aurelia (po konfigurácii) píšete v jazykoch ES6 alebo TypeScript a šablóny vyzerajú ako absolútne rozumné HTML, najmä v porovnaní s Angular. Aurelia je konvencia konfigurácie a v 95% prípadov budete v poriadku s použitím predvolených konvencií (ako je pomenovanie šablón, pomenovanie prvkov atď.), Zatiaľ čo Angular vyžaduje, aby ste konfiguráciu poskytli v podstate pre všetko.
Aurelia sa tiež považuje za viac vyhovujúcu štandardom, už len preto, že nerozlišuje veľké a malé písmená, pokiaľ ide o značky HTML, zatiaľ čo Angular 2 áno. To znamená, že Angular 2 sa nemôže spoliehať na syntaktický analyzátor HTML prehliadača, takže si vytvorili svoj vlastný.
Ďalším faktorom, ktorý treba brať do úvahy pri výbere medzi rámcami SPA, je komunita - ekosystém - okolo nich. Angular aj Aurelia majú všetky základné informácie (smerovač, šablóna, overovanie atď.) A je ľahké získať natívny modál alebo použiť knižnicu tretích strán, ale nie je prekvapením, že Angular má väčšiu komunitu a väčší rozvoj tím.
Aj keď sú oba rámce open source, Angular je vyvíjaný hlavne spoločnosťou Google a jeho účelom nie je komercializácia, zatiaľ čo spoločnosť Durandal, Inc., ktorá zamestnáva hlavný tím, sleduje Ember.js “ model monetizácie prostredníctvom konzultácií a školení.
Pozrime sa na niektoré z najvýznamnejších prvkov, ktoré podčiarkujú filozofiu každého rámca.
Po klonovaní osiva projekty pre Uhlové a Aurelia , máme aplikáciu ES6 Aurelia (môžete použiť Jspm / System.js, Webpack a RequireJS v kombinácii s ES6 alebo TypeScript) a aplikáciu TypeScript Angular (WebPack).
Podme na to.
Predtým, ako porovnáme pracovné príklady vedľa seba, musíme sa pozrieť na niekoľko syntaktických rozdielov medzi Aureliou a Angular 2, konkrétne v kľúčovej funkcii hodnôt väzby z radiča na pohľad. Angular 1 použil na všetko „špinavú kontrolu“, čo bola metóda, ktorá skenovala rozsah zmien. To pochopiteľne spôsobilo množstvo problémov s výkonom. Ani Angular 2, ani Aurelia nešli touto cestou. Namiesto toho používajú väzbu udalostí.
V Angular viazate údaje hranatými zátvorkami a na viazanie udalostí používate zátvorky, napríklad takto:
Obojsmerná väzba - ak chcete, aby sa zmeny v údajoch aplikácie odrážali od pohľadu a naopak - je kombináciou hranatých aj zátvoriek. Pre obojsmerne viazaný vstup by to teda fungovalo dobre:
{{text}}
Inými slovami, zátvorky predstavujú udalosť, zatiaľ čo hranaté zátvorky predstavujú hodnotu, ktorá sa tlačí na vstup.
Tím Angular urobil skvelú prácu pri oddeľovaní záväzných pokynov: do DOM, od DOM a obojsmerný. Existuje tiež veľa syntaxového cukru súvisiaceho s triedami a štýlmi viazania. Zoberme si napríklad nasledujúci úryvok ako príklad jednosmernej väzby:
{{ text }} import {Component, Input} from '@angular/core'; @Component(/* ... */) export class MyComponent { @Input() text : string; } Text in child: {{ text }}
Čo však v prípade, že chceme viazať obojsmerné údaje na komponent? Zvážte nasledujúce základné nastavenie vstupu:
ngModel
Upozorňujeme, že ak chcete použiť @angular/forms
, váš modul musí importovať FormsModule z property name + 'Change'
. Teraz tu máme niečo zaujímavé. Aktualizácia hodnoty v nadradenom vstupe zmení hodnoty všade, ale úprava vstupu dieťaťa ovplyvní iba dané dieťa. Ak chceme, aby aktualizoval nadradenú hodnotu, potrebujeme udalosť, ktorá informuje nadradeného človeka. Konvencia pomenovania tejto udalosti je import {Component, Input, Output, EventEmitter} from '@angular/core'; @Component(/* ... */) export class MyComponent { @Input() text : string; @Output() textChange = new EventEmitter(); triggerUpdate() { this.textChange.emit(this.text); } }
, napríklad takto:
ngModelChange
Obojsmerná väzba začne fungovať správne hneď po vytvorení väzby na changeDetection: ChangeDetectionStrategy.OnPush
udalosť:
property='${value}'
Čo s jednorazovou väzbou, keď efektívne poviete rámcu, aby ignoroval viazané hodnoty, aj keď sa menia?
V Angular 1 sme na väzbu použili raz {{:: value}}. V Angular 2 sa komplikuje jednorazová väzba: dokumentácia hovorí, že môžete použiť property.one-time='value' property.one-way='value' property.two-way='value'
v konfigurácii komponentu, ale to urobí všetko vaše viazanie jednorazovo.
Na rozdiel od Angular 2 je viazanie údajov a udalostí v Aurelii naozaj jednoduché. Môžete použiť interpoláciu, rovnako ako Angular’s property.bind='value'
, alebo jeden z nasledujúcich typov väzieb:
@bindable
Názvy sú samy osebe. Ďalej existuje @Input
, čo je syntaxový cukor, ktorý sám detekuje, či má byť väzba jednosmerná alebo obojsmerná. Zvážte:
.trigger
Vo vyššie uvedenom úryvku obidve .delegate
a // child.js this.element.dispatchEvent(new CustomEvent('change', { detail: someDetails }));
sú konfigurovateľné, takže môžete ľahko meniť veci, ako je názov viazanej vlastnosti, atď.
Čo udalosti? Na vytvorenie väzby na udalosti v Aurelii používate .trigger
a .delegate
. Napríklad ak chcete, aby podradený komponent spustil udalosť, môžete urobiť nasledovné:
náklady na prepínanie v piatich silách
document
Potom si to v prípade rodiča vypočuť:
awesome-svg
Rozdiel medzi týmito dvoma je v tom, že // awesome-svg.js import {bindable} from 'aurelia-framework'; export class AwesomeSvgCustomElement { @bindable title; @bindable colors = []; }
vytvorí obslužný program udalostí na danom konkrétnom prvku, zatiaľ čo @template
pridá poslucháča na @inlineView
. Šetria sa tým zdroje, ale v prípade neblikajúcich udalostí to zjavne nebude fungovať.
Teraz, keď sme pokryli väzbu, vytvorme základnú súčasť, ktorá vykreslí škálovateľnú vektorovú grafiku (SVG). Bude to úžasné, preto to nazveme @noView
. Toto cvičenie ilustruje základné funkcie a filozofiu pre Aurelia a Angular 2. Príklady kódov Aurelia tohto článku sú k dispozícii na GitHub .
Najprv si vytvoríme súbor JavaScript:
.html
Teraz k HTML.
V Aurelii môžete určiť šablónu (alebo použiť vloženú) s anotáciami .js
, @customElement('awesome-svg')
alebo dokonca awesome-svg
, ale po vybalení z krabice vyhľadá js
súbor s rovnakým názvom ako awesome-svg.html
spis. To isté platí pre názov vlastného prvku - môžete ho nastaviť pomocou
, ale ak tak neurobíte, Aurelia prevedie nadpis na pomlčku a hľadá zhodu.
Pretože sme neurčili inak, prvok sa bude volať .html
a Aurelia vyhľadá šablónu s rovnakým názvom ako @containerless
súbor (t.j. rect
) v rovnakom adresári:
@containerless
Vlastný prvok bude pomenovaný podľa názvu súboru. Jediný rozdiel od pomenovania ďalších komponentov je ten, že pri importe, či už v konfigurácii alebo cez značku, by ste mali vložiť @containerless
nakoniec. Takže napríklad :.
Aurelia má tiež vlastné atribúty, ale neslúžia na ten istý účel ako v Angular 2. Napríklad v Aurelii môžete použiť custom-rect
anotácia k vlastnému NumberOperator
prvok. NumberGenerator
je možné použiť aj s vlastnými šablónami bez ovládača a, ktoré v podstate vykresľujú obsah do DOM.
Zvážte nasledujúci kód obsahujúci import {inject} from 'aurelia-framework'; import {NumberGenerator} from './number-generator' export class NumberGenerator { getNumber(){ return 42; } } @inject(NumberGenerator) export class NumberOperator { constructor(numberGenerator){ this.numberGenerator = numberGenerator; this.counter = 0; } getNumber(){ return this.numberGenerator.getNumber() + this.counter++; } }
anotácia:
import {inject} from 'aurelia-framework'; import {NumberOperator} from './_services/number-operator'; @inject(NumberOperator) export class SomeCustomElement { constructor(numberOperator){ this.numberOperator = numberOperator; //this.numberOperator.getNumber(); } }
Výstup by neobsahoval značku vlastného prvku (Factory
), ale namiesto toho dostaneme:
NewInstance
Pokiaľ ide o služby, Aurelia a Angular sú si veľmi podobné, ako uvidíte v nasledujúcich príkladoch. Predpokladajme, že potrebujeme import { Factory, NewInstance } from 'aurelia-framework'; @inject(SomeService) export class Stuff { constructor(someService, config){ this.someService = someService; } } @inject(Factory.of(Stuff), NewInstance.of(AnotherService)) export class SomethingUsingStuff { constructor(stuffFactory, anotherService){ this.stuff = stuffFactory(config); this.anotherServiceNewInstance = anotherService; } }
čo závisí od import { Injectable } from '@angular/core'; import { NumberGenerator } from './number-generator'; @Injectable() export class NumberGenerator { getNumber(){ return 42; } } @Injectable() export class NumberOperator { counter : number = 0; constructor(@Inject(NumberGenerator) private numberGenerator) { } getNumber(){ return this.numberGenerator.getNumber() + this.counter++; } }
.
Tu je postup, ako definovať naše dve služby v Aurelii:
@Injectable
Teraz pre komponent vstrekujeme rovnakým spôsobom:
@Component({ //... providers: [NumberOperator, NumberGenerator] })
Ako vidíte, s injekciou závislostí môže byť ktorákoľvek trieda plne rozšíriteľnou službou, takže môžete napísať aj svoje vlastné prekladače.
Ak potrebujete továreň alebo novú inštanciu (bootstrap(AppComponent, [NumberGenerator, NumberOperator])
a NumberOperator
je len niekoľko populárnych riešení, ktoré sú k dispozícii po vybalení z krabice), môžete urobiť nasledovné:
NumberGenerator
Rovnaká sada služieb v Angular 2:
@Component({ //... providers: [NumberOperator, NumberGenerator], }) export class SomeComponent { constructor(@Inject(NumberOperator) public service){ //service.getNumber(); } }
The provide
je nutná anotácia a na skutočné vloženie služby je potrebné službu špecifikovať v zozname poskytovateľov v konfigurácii komponentu alebo celej konfigurácii modulu, napríklad takto:
let stuffFactory = (someService: SomeService) => { return new Stuff(someService); } @Component({ //... providers: [provide(Stuff, {useFactory: stuffFactory, deps: [SomeService]})] })
Alebo sa to neodporúča, môžete to určiť aj v znakoch ng-transclude
hovor.
Upozorňujeme, že je potrebné uviesť obidve @Component({ selector: 'child', template: `Transcluded: ` }) export class MyComponent {}
a Hello from Translusion Component
bez ohľadu na to, ako si ho vpichnete.
Výsledný komponent bude vyzerať asi takto:
Yes
V Angular 2 môžete vytvárať továrne pomocou @Component
anotácia, ktorá sa tiež používa na aliasingové služby, aby sa zabránilo kolíziám mien. Vytvorenie továrne môže vyzerať takto:
Slot 1:
Slot 2:
Úhlová 1 mala schopnosť zahrnúť obsah, „slot“ z jednej šablóny do druhej pomocou vylúčenia. Pozrime sa, čo jej potomkovia môžu ponúknuť.
V Angular 2 sa vylúčenie nazýva „projekcia obsahu“ a funguje rovnako ako Hello from Translusion Component again Hello from Translusion Component
urobil; to znamená, že keď hovoríme v termínoch Angular 1, použije sa pre translokovaný obsah rodičovský rozsah. Bude zodpovedať značke vylúčeného obsahu na základe selektora konfigurácie. Zvážte:
select
Potom môžete komponent použiť s Slot: ${textValue}
a dostaneme presný preložený element cannot have content
HTML vykreslený v podradenej súčasti.
Pre viac slotovú transláciu má Angular 2 selektory, ktoré môžete použiť rovnakým spôsobom ako pre Slot A:
konfigurácia:
Slot B: Slot C: Fallback Content A value B value
view-model
ComponentResolver
rozdiel medzi umením a dizajnom
Môžete použiť @useShadowDOM
na svojich vlastných značkách, nezabudnite však, že značka musí byť aplikácii Angular 2 známa.
Pamätáte si, keď som povedal, že Aurelia dodržiava webové štandardy, kedykoľvek je to možné? V Aurelii sa translácia nazýva sloty a je to len polyfill pre Web Components Shadow DOM. Tieňový DOM nie je vytvorený pre sloty ešte , ale nasleduje Špecifikácie W3C .
import {useShadowDOM} from 'aurelia-framework'; @useShadowDOM() export class YetAnotherCustomElement {}
Aurelia bola navrhnutá tak, aby vyhovovala štandardom, a Angular 2 nie. Vďaka tomu môžeme robte s úžasnými automatmi Aurelie ďalšie úžasné veci , ako použiť záložný obsah (pokus o použitie záložného obsahu v Angular 2 zlyhá s ViewEncapsulation.Native
). Zvážte:
import { Component, ViewEncapsulation } from '@angular/core'; @Component({ //... encapsulation: ViewEncapsulation.Native, }) export class YetAnotherComponent {}
Rovnakým spôsobom ako Angular 2 vykreslí Aurelia všetky výskyty automatu na základe zhody mien.
Za zmienku tiež stojí, že v Aurelii aj Angular môžete kompilovať časti šablón a komponenty vykresliť dynamicky (pomocou znakov
|_+_|v Aurelii alebo
|_+_|v Angular 2).
Aurelia aj Angular podporujú Shadow DOM.
V Aurelii stačí použiť
dekoratér a ste pripravení vyraziť:|_+_|
V Angular to isté možno urobiť s
|_+_|:
Nezabudnite skontrolovať, či máte prehľadávač podporuje Shadow DOM.
Píše sa rok 2017 a vykresľovanie na strane servera je veľmi trendy. Už môžete vykresliť Angular 2 na back-ende pomocou Uhlová univerzálna , a Aurelia ich bude mať v roku 2017, ako je uvedené v jeho novoročné predsavzatia . V skutočnosti existuje spustiteľné demo v repre Aurelie.
Okrem toho má Aurelia možnosti progresívneho vylepšenia už viac ako rok, čo Angular 2 nemá kvôli svojej neštandardnej syntaxi HTML.
Aj keď nám to neukazuje celý obrázok, benchmarky DBMonster s predvolenými konfiguráciami a optimalizovanou implementáciou vytvárajú dobrý porovnávací obrázok: Aurelia a Angular vykazujú podobné výsledky približne 100 opätovných vykreslení za sekundu (testované na MacBooku Pro), zatiaľ čo Angular 1 ukázal niečo okolo polovice tohto výsledku. Aurelia aj Angular prekonávajú Angular 1 asi päťkrát a obe sú o 40% pred Reactom. Aurelia ani Angular 2 nemajú implementáciu Virtual DOM.
Pokiaľ ide o veľkosť, Angular je zhruba dvakrát tak tučný ako Aurelia, ale chlapci z Googlu na tom pracujú: Plán Angular obsahuje uvoľnenie Angular 4 s plánmi, ako ho zmenšiť a odľahčiť, a zároveň vylepšiť skúsenosti vývojárov. Neexistuje Angular 3 a v skutočnosti by sa pri verzii Angular malo číslo verzie znížiť, pretože hlavné vydania sa plánujú každých 6 mesiacov. Ak sa pozriete na cestu, ktorú Angular prešiel z verzie alfa do jej súčasnej verzie, uvidíte, že to nebolo vždy koherentné s vecami, ako sú napríklad premenovanie atribútov z jednej verzie na druhú, atď. Tím Angular sľubuje, že prelomenie zmien bude ľahké migrovať.
Od roku 2017 plánuje tím Aurelia vydať Aurelia UX, poskytnúť viac integrácií a nástrojov a implementovať vykresľovanie na strane servera (ktoré je v pláne veľmi dlho).
Angular aj Aurelia sú dobré a výber jedného pred druhým je vecou osobného vkusu a priorít. Ak potrebujete štíhlejšie riešenie, Aurelia je vaša najlepšia voľba, ale ak potrebujete podporu komunity, Angular je váš víťaz. Nejde o otázku „Umožňuje mi tento rámec…?“ pretože odpoveď je jednoducho „áno“. Poskytujú zhruba rovnakú funkcionalitu pri sledovaní rôznych filozofií a štýlov spolu s úplne odlišným prístupom k webovým štandardom.