ngrx-actions ⚡️ Actions and Reducer Utilities for

我要开发同款
匿名用户2021年12月09日
30阅读
开发技术JavaScript
所属分类Web应用开发、Web框架
授权协议MIT License

作品详情

NGRXActions

Actions/reducerutilityforNGRX.ItprovidesahandfuloffunctionstomakeNGRX/ReduxmoreAngular-tastic.

@Store(MyInitialState):Decoratorfordefaultstateofastore.@Action(...MyActionClass:Action[]):Decoratorforaactionfunction.@Effect(...MyActionClass:Action[]):Decoratorforaeffectfunction.ofAction(MyActionClass):LettableoperatorforNGRXEffectscreateReducer(MyStoreClass):Reducerbootstrapfunction@Select('my.prop'):Selectdecorator

Inspiredbyredux-actandredux-actionsforRedux.

Seechangelogforlatestchanges.

NOTE:IrecommendcheckingoutmylatestlibrarycalledNGXS.

Whatsthisfor?

ThisissugartohelpreduceboilerplatewhenusingReduxpatterns.Thatsaid,here'sthehighlevelofwhatitprovides:

ReducersbecomeclassessoitsmorelogicalorganizationAutomaticallycreatesnewinstancessoyoudon'thavetohandlespreadseverywhereEnablesbettertypecheckinginsideyouractionsReduceshavingtopasstypeconstantsbyusingtypechecking

Itsdeadsimple(<100LOC)andyoucanpickandchoosewhereyouwanttouseit.

GettingStarted

Togetstarted,letsinstallthepackagethrunpm:

npmingrx-actions--SReducers

Next,createanactionjustlikeyoudowithNGRXtoday:

exportclassMyAction{readonlytype='MyAction';constructor(publicpayload:MyObj){}}

thenyoucreateaclassanddecorateitwithaStoredecoratorthatcontainstheinitialstateforyourreducer.WithinthatclassyoudefinemethodsdecoratedwiththeActiondecoratorwithanargumentoftheactionclassyouwanttomatchiton.

import{Store,Action}from'ngrx-actions';@Store({collection:[],selections:[],loading:false})exportclassMyStore{@Action(Load,Refresh)load(state:MyState,action:Load){state.loading=true;}@Action(LoadSuccess)loadSuccess(state:MyState,action:LoadSuccess){state.collection=[...action.payload];}@Action(Selection)selection(state:MyState,action:Selection){state.selections=[...action.payload];}@Action(DeleteSuccess)deleteSuccess(state:MyState,action:DeleteSuccess){constidx=state.collection.findIndex(r=>r.myId===action.payload);if(idx===-1){returnstate;}constcollection=[...state.collection];collection.splice(idx,1);return{...state,collection};}}

Youmaynotice,Idon'treturnthestate.Thatsbecauseifitdoesn'tseeastatereturnedfromtheactionitinspectswhetherthestatewasanobjectorarrayandautomaticallycreatesanewinstanceforyou.Ifyouaremutatingdeeplynestedproperties,youstillneedtodealwiththoseyourself.

Youcanstillreturnthestateyourselfanditwon'tmesswithit.Thisishelpfulforifthestatedidn'tchangeoryouhavesomecomplexlogicgoingon.ThiscanbeseeninthedeleteSuccessaction.

Aboveyoumaynotice,thefirstactionhasmultipleactionclasses.Thatsbecausethe@Actiondecoratorcanacceptsingleormultipleactions.

TohookituptoNGRX,allyouhavetodoiscallthecreateReducerfunctionpassingyourstore.NowpassthemyReducerjustlikeyouwouldafunctionwithaswitchstatementinside.

import{createReducer}from'ngrx-actions';exportfunctionmyReducer(state,action){returncreateReducer(MyStore)(state,action);}

Intheaboveexample,IreturnafunctionthatreturnsmycreateReducer.ThisisbecauseAoTcomplainsstatingFunctionexpressionsarenotsupportedindecoratorsifwejustassignthecreateReducermethoddirectly.ThisisaknownissueandotherNGRXthingssufferfromittoo.

Next,passthattoyourNGRXmodulejustlikenormal:

@NgModule({imports:[StoreModule.forRoot({pizza:pizzaReducer})]})exportclassAppModule{}

OptionallyyoucanalsoprovideyourstoredirectlytotheNgrxActionsModuleanditwillhandlecreatingthereducerforyouandalsoenablestheabilitytouseDIwithyourstores.SoratherthandescribinginforRootorforFeaturewithStoreModule,wecallthemonNgrxActionsModule.

@NgModule({imports:[NgrxActionsModule.forRoot({pizza:PizzaStore})],providers:[PizzaStore]})exportclassAppModule{}Effects

IfyouwanttouseNGRXeffects,I'vecreatedalettableoperatorthatwillallowyoutopasstheactionclassastheargumentlikethis:

import{ofAction}from'ngrx-actions';@Injectable()exportclassMyEffects{constructor(privateupdate$:Actions,privatemyService:MyService){}@Effect()Load$=this.update$.pipe(ofAction(Load),switchMap(()=>this.myService.getAll()),map(res=>newLoadSuccess(res)));}

In3.x,weintroducedanewdecoratorcalled@Effectthatyoucandefineinyourstoretoperformasyncoperations.

@Store({delievered:false})exportclassPizzaStore{constructor(privatepizzaService:PizzaService){}@Action(DeliverPizza)deliverPizza(state){state.delivered=false;}@Effect(DeliverPizza)deliverPizzaToCustomer(state,{payload}:DeliverPizza){this.pizzaService.deliver(payload);}}

Effectsarealwaysrunafteractions.

Selects

Wedidn'tleaveoutselectors,thereisaSelectdecoratorthatacceptsa(deep)pathstring.Thislookslike:

@Component({...})exportclassMyComponent{//Functions@Select((state)=>state.color)color$:Observable<string>;//Arrayofprops@Select(['my','prop','color'])color$:Observable<strinv>;//Deeplynestedproperties@Select('my.prop.color')color$:Observable<string>;//Impliedbythenameofthemember@Select()color:Observable<string>;//Remaptheslicetoanewobject@Select(state=>state.map(f=>'blue'))color$:Observable<string>;}

Thiscanhelpcleanupyourstoreselects.Tohookitup,intheAppModuleyoudo:

import{NgrxActionsModule}from'ngrx-actions';@NgModule({imports:[NgrxActionsModule]})exportclassAppModule{}

Andyoucanstartusingitinanycomponent.Italsoworkswithfeaturestorestoo.Note:TheSelectdecoratorhasalimitationoflackoftypecheckingduetoTypeScript#4881.

CommonQuestionsWhataboutcomposition?Wellsinceitcreatesanormalreducerfunction,youcanstilluseallthesamecompositionfnsyoualreadyuse.WillthisworkwithnormalRedux?WhileitsdesignedforAngularandNGRXitwouldworkperfectlyfinefornormalRedux.Ifthatgetsrequested,I'llbehappytoaddbettersupporttoo.DoIhavetorewritemyentireapptousethis?No,youcanusethisincombinationwiththetranditionalswitchstatementsorwhateveryouarecurrentlydoing.DoesitsupportAoT?Yesbutseeaboveexamplefordetailsonimplementation.DoesthisworkwithNGRXDevTools?Yes,itdoes.Howdoesitworkwithtesting?Everythingshouldworkthesamewaybutdon'tforgetifyouusetheselectortooltoincludethatinyourtestrunnerthough.CommunityReducingBoilerplatewithNGRX-ACTIONSAdventuresinAngular:NGRXBoilerplateIntroducingNGRX-Actions3.0
声明:本文仅代表作者观点,不代表本站立场。如果侵犯到您的合法权益,请联系我们删除侵权资源!如果遇到资源链接失效,请您通过评论或工单的方式通知管理员。未经允许,不得转载,本站所有资源文章禁止商业使用运营!
下载安装【程序员客栈】APP
实时对接需求、及时收发消息、丰富的开放项目需求、随时随地查看项目状态

评论