angular 2. Pipes. Cannot read property of undefine

2019-02-25 19:14发布

i made a pipe

@Pipe({
  name: 'orgFilter'
})
export class OrgFilterPipe implements PipeTransform {
    transform(orgs: Organization[], args: String[]): any {
        console.log(orgs)
       let filter = args[0].toLowerCase();
       return filter ? orgs.filter((org:Organization) => org.name.toLowerCase().indexOf(filter) != -1): orgs;
}

and using it in html:

<tbody>
        <tr *ngFor="#organization of organizations | orgFilter:listFilter.value">
            <td>{{ organization.organizationName }}</td>
            <td>{{ organization.city }}</td>
            <td>{{ organization.state }}</td>
            <td>{{ organization.country }}</td>
            <td>
                <i class="material-icons">mode_edit</i>
            </td>
            <td>
                <i class="material-icons">delete</i>
            </td>
        </tr>
        <tr>
            <td>
                <div class="col-md-4"><input type="text" #listFilter (keyup)="0" /></div>
            </td>
            <td></td>
            <td></td>
            <td></td>
            <td></td>
            <td></td>
        </tr>
</tbody>

i am getting an error browser_adapter.js:84 TypeError: Cannot read property 'toLowerCase' of undefined at t.transform (orgFilter.ts:9)

the problem lies in let filter = args[0].toLowerCase();

what is causing it? does this mean that args doesn't have any values? should i declare it somewhere? am i using pipe wrong in html? if i remove the pipe i see table with data. but when i put it into html the data disappears and there is only this input field in the table

2条回答
对你真心纯属浪费
2楼-- · 2019-02-25 19:41

Given the template you provided, it looks like instances of Organization have no member called "name", but a member called "organizationName" instead.

Maybe you can try replacing

org.name.toLowerCase().indexOf(filter) != -1

with

org.organizationName.toLowerCase().indexOf(filter) != -1

in your code.

UPDATE

That said, you can try a different way of binding you filter expression:

@Pipe({
  name: 'orgFilter'
})
export class OrgFilterPipe implements PipeTransform {
    transform(orgs: Organization[], expression:string): any {
       if(!expression){
            return orgs;
       }
       else {
            return orgs.filter((org:Organization) => org.organizationName.toLowerCase().indexOf(expression) != -1)
       }
} 

Where expression refers to a member of your component, let's say:

filterExpression: string;

Then change your input text to:

<input type="text" [(ngModel)]="filterExpression">

And change the pipe call to:

<tr *ngFor="#organization of organizations | orgFilter:filterExpression">

According to the documentation for a list filter you may have to declare your pipe as impure using:

@Pipe({
  name: 'orgFilter',
  pure: false

})
查看更多
Summer. ? 凉城
3楼-- · 2019-02-25 19:44

It's either going to be the args aren't defined or the org.name isn't defined. You could try debugging it in the DevTools, maybe set the breakpoint at the start of the transform()

查看更多
登录 后发表回答