Angular 4.0.0 custom pipe always sending undefined -


i trying create custom filter filter array of objects object's title attribute, , display objects title contains search substring. problem is, undefined gets passed pipe component.

the pipe used in template in *ngfor loop. template code looks this:

<div class="col-md-2" *ngfor="let strategy of (strategies | namefilter: searchstrategytext)"> 

in context, strategies array of strategy objects, searchstrategytext string two-way data binding input field.

the custom pipe code follows:

import {injectable, pipe, pipetransform} '@angular/core'; import {strategy} './strategy';  @pipe({   name: 'namefilter' }) @injectable() export class namefilter implements pipetransform {   transform(strategies: strategy[], searchstring: string): strategy[] {     return strategies.filter(strategy => strategy.title.indexof(searchstring) !== -1);   } } 

the versions of angular using follows:

angular-cli: 1.0.0-beta.28.3 node: 6.9.2 os: darwin x64 @angular/common: 4.0.0 @angular/compiler: 4.0.0 @angular/core: 4.0.0 @angular/forms: 4.0.0 @angular/http: 4.0.0 @angular/platform-browser: 4.0.0 @angular/platform-browser-dynamic: 4.0.0 @angular/router: 4.0.0 

i have scoured internet , tried variety of approaches, approach seemed closest angular describes here: https://angular.io/docs/ts/latest/guide/pipes.html

what missing here? if left out important info, let me know.

edit: html input section two-way data binding searchstrategytext:

<div class="form-group has-feedback has-feedback-left">                 <input class="form-control" [(ngmodel)]="searchstrategytext" name="searchstrategytext" (focus)="selectallcontent($event)" type="text" placeholder="strategy search">                 <i class="glyphicon glyphicon-search form-control-feedback"></i>             </div> 

i make custom pipe globally available via appmodule importing , adding declarations array.

edit #2: getting strategies array strategyservice have mocked getstrategies() function returns mock data class.

code component gets strategies service:

getstrategies(): void {     this.strategyservice.getstrategies().then(strategies => this.strategies = strategies);   } 

strategyservice component:

import { injectable } '@angular/core'; import { strategy } './strategy'; import { strategies } './mock-strategies'; import { active_strategies } './mock-active-strategies';  @injectable() export class strategyservice {   getstrategies(): promise<strategy[]> {     return promise.resolve(strategies);   }    getactivestrategies(): promise<strategy[]>{     return promise.resolve(active_strategies);   }  } 

mock data component:

import { strategy } './strategy';  export const strategies: strategy[] = [     {title: "key reverse long entry",         description: "lorem ipsum dolor sit amet, consectetur adipiscing elit.",         type: "strategy template",         modifiedtime: 1461155000,         symbollist:"s&p 100",         deploystatus:"load",         action:"buy",         isactive: false},     {title:"key reverse short entry",         description:"lorem ipsum dolor sit amet, consectetur adipiscing elit.",         type:"strategy template",         modifiedtime: 1461154940,         symbollist:"s&p 100",         deploystatus:"unload",         action:"buy",         isactive: false} ]; 

there's lot more mock data, shortened brevity.

edit #3: strategylist component controlling of this:

import { component, oninit, viewchild } '@angular/core';  import { tabsetcomponent } 'ng2-bootstrap';  import { strategy } './strategy'; import { strategyservice } './strategy.service';  @component({   selector: 'strategy-list',   templateurl: './strategy-list.component.html',   styleurls: ['./strategy-list.component.css'] })  export class strategylistcomponent implements oninit {   @viewchild('statictabs') statictabs: tabsetcomponent;   strategies: strategy[];   activestrategies: strategy[] = [];   totalitems = 0; // previous html: (allsignals | filter:searchsignaltext).length   filterselected = false;   searchstrategytext: string;    constructor(private strategyservice: strategyservice) { }    ngoninit() {     this.getstrategies();     this.searchstrategytext = "initial";   }    selecttab(tab_id: number){     this.statictabs.tabs[tab_id].active = true;   }    getstrategies(): void {     this.strategyservice.getstrategies().then(strategies => this.strategies = strategies);   }    getactivestrategies(): void {     this.strategyservice.getactivestrategies().then(activestrategies => this.activestrategies = activestrategies);   }    exists(strategy: strategy): boolean {     let idx = this.activestrategies.indexof(strategy);     if ( idx > -1){       console.log('strategy active');       return true;     } else {       console.log('strategy inactive');       return false;     }   }    toggle(strategy: strategy): void {     let idx = this.activestrategies.indexof(strategy);     if (idx > -1){       console.log("strategy exists in activestrategies");       this.activestrategies.splice(idx, 1);       // this.strategyservice.cancelstrategy(strategy);     }     else {       console.log("strategy not exist in activestrategies");       this.activestrategies.push(strategy);       // this.strategyservice.activatestrategy(strategy);     }    }    togglefilter(): void{     this.filterselected = !this.filterselected;   }  } 

edit #4: error output:

strategy-list.component.html:9 error context debugcontext_ {view: object, nodeindex: 3, nodedef: object, eldef: object, elview: object} view_strategylistcomponent_2 @ strategy-list.component.html:9 debugcontext_.logerror @ services.ts:571 errorhandler.handleerror @ error_handler.ts:69 (anonymous) @ application_ref.ts:286 zonedelegate.invoke @ zone.js:365 oninvoke @ ng_zone.ts:261 zonedelegate.invoke @ zone.js:364 zone.run @ zone.js:125 (anonymous) @ zone.js:760 zonedelegate.invoketask @ zone.js:398 oninvoketask @ ng_zone.ts:253 zonedelegate.invoketask @ zone.js:397 zone.runtask @ zone.js:165 drainmicrotaskqueue @ zone.js:593 zonetask.invoke @ zone.js:464 zone.js:569 unhandled promise rejection: cannot read property 'filter' of undefined ; zone: <root> ; task: promise.then ; value: typeerror: cannot read property 'filter' of undefined     @ namefilter.transform (name-filter.pipe.ts:11)     @ object.eval [as updatedirectives] (strategy-list.component.html:9)     @ object.debugupdatedirectives [as updatedirectives] (services.ts:273)     @ checkandupdateview (view.ts:345)     @ callviewaction (view.ts:700)     @ execembeddedviewsaction (view.ts:670)     @ checkandupdateview (view.ts:389)     @ callviewaction (view.ts:700)     @ execcomponentviewsaction (view.ts:644)     @ checkandupdateview (view.ts:392)     @ callviewaction (view.ts:700)     @ execcomponentviewsaction (view.ts:644)     @ checkandupdateview (view.ts:392)     @ callwithdebugcontext (services.ts:645)     @ object.debugcheckandupdateview [as checkandupdateview] (services.ts:215) typeerror: cannot read property 'filter' of undefined     @ namefilter.transform (http://localhost:3000/app/name-filter.pipe.js:13:26)     @ object.eval [as updatedirectives] (ng:///appmodule/strategylistcomponent.ngfactory.js:89:66)     @ object.debugupdatedirectives [as updatedirectives] (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12620:21)     @ checkandupdateview (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12032:14)     @ callviewaction (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12347:17)     @ execembeddedviewsaction (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12319:17)     @ checkandupdateview (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12033:5)     @ callviewaction (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12347:17)     @ execcomponentviewsaction (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12293:13)     @ checkandupdateview (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12038:5)     @ callviewaction (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12347:17)     @ execcomponentviewsaction (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12293:13)     @ checkandupdateview (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12038:5)     @ callwithdebugcontext (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:13020:42)     @ object.debugcheckandupdateview [as checkandupdateview] (http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:12560:12) consoleerror @ zone.js:569 handleunhandledrejection @ zone.js:574 _loop_1 @ zone.js:609 drainmicrotaskqueue @ zone.js:613 zonetask.invoke @ zone.js:464 zone.js:571 error: uncaught (in promise): typeerror: cannot read property 'filter' of undefined typeerror: cannot read property 'filter' of undefined     @ namefilter.transform (name-filter.pipe.ts:11)     @ object.eval [as updatedirectives] (strategy-list.component.html:9)     @ object.debugupdatedirectives [as updatedirectives] (services.ts:273)     @ checkandupdateview (view.ts:345)     @ callviewaction (view.ts:700)     @ execembeddedviewsaction (view.ts:670)     @ checkandupdateview (view.ts:389)     @ callviewaction (view.ts:700)     @ execcomponentviewsaction (view.ts:644)     @ checkandupdateview (view.ts:392)     @ callviewaction (view.ts:700)     @ execcomponentviewsaction (view.ts:644)     @ checkandupdateview (view.ts:392)     @ callwithdebugcontext (services.ts:645)     @ object.debugcheckandupdateview [as checkandupdateview] (services.ts:215)     @ namefilter.transform (name-filter.pipe.ts:11)     @ object.eval [as updatedirectives] (strategy-list.component.html:9)     @ object.debugupdatedirectives [as updatedirectives] (services.ts:273)     @ checkandupdateview (view.ts:345)     @ callviewaction (view.ts:700)     @ execembeddedviewsaction (view.ts:670)     @ checkandupdateview (view.ts:389)     @ callviewaction (view.ts:700)     @ execcomponentviewsaction (view.ts:644)     @ checkandupdateview (view.ts:392)     @ callviewaction (view.ts:700)     @ execcomponentviewsaction (view.ts:644)     @ checkandupdateview (view.ts:392)     @ callwithdebugcontext (services.ts:645)     @ object.debugcheckandupdateview [as checkandupdateview] (services.ts:215)     @ resolvepromise (zone.js:712) [<root>]     @ :3000/node_modules/zone.js/dist/zone.js:638:17 [<root>]     @ :3000/node_modules/zone.js/dist/zone.js:654:33 [<root>]     @ zone.run (zone.js:125) [<root> => <root>]     @ :3000/node_modules/zone.js/dist/zone.js:760:57 [<root>]     @ zone.runtask (zone.js:165) [<root> => <root>]     @ drainmicrotaskqueue (zone.js:593) [<root>]     @ xmlhttprequest.zonetask.invoke (zone.js:464) [<root>] 

you need add check if if strategies exist or not clled method inside filter because first time filter called strategies undefined or initialize strategies empty error in component

transform(strategies: strategy[], searchstring: string): strategy[] { if(strategies){ return strategies.filter(strategy => strategy.title.indexof(searchstring) !== -1);} }  

rest of code

export class appcomponent implements oninit {   title = 'app works!';   strategies = [];    constructor(private strategyservice: strategyservice) { }    ngoninit() {     this.getstrategies();   }    getstrategies(): void {     this.strategyservice.getstrategies().then((strategies) => this.strategies = strategies);   } } 

in service

@injectable() export class strategyservice {     getstrategies() {         return promise.resolve(strategies);     }  }  export const strategies = [     {         title: "key reverse long entry",         description: "lorem ipsum dolor sit amet, consectetur adipiscing elit.",         type: "strategy template",         modifiedtime: 1461155000,         symbollist: "s&p 100",         deploystatus: "load",         action: "buy",         isactive: false     },     {         title: "key reverse short entry",         description: "lorem ipsum dolor sit amet, consectetur adipiscing elit.",         type: "strategy template",         modifiedtime: 1461154940,         symbollist: "s&p 100",         deploystatus: "unload",         action: "buy",         isactive: false     } ]; 

and filter

    @pipe({         name: 'namefilter'     })     export class namefilter implements pipetransform {         transform(strategies: string[], searchstring: string): string[] { if(strategies) //make sure run check otherwise strategies undefined first time{ return strategies;}          }     } 

first filter gets called empty array , final results https://ibb.co/mzarva https://ibb.co/


Comments