Búsqueda de sitios web

javascript - Filtro global personalizado en PrimeNG (FilterService)


Me estaba enfrentando a un problema al filtrar la p-table en PrimeNG. Escenario:

tabla que contiene: John Kelvin Doe

Clave de búsqueda: John Doe

esperado: 1 fila, estaba obteniendo 0 filas usando filtros incorporados;

Intenté los filtros integrados, pero estaba obteniendo 0 registros.

He creado un Filtro Global Personalizado que verifica si la entrada tiene dos palabras y luego comprueba los filtros startsWith y endsWith.

onGlobalFilter(table: Table, event: Event) {
    table.filterGlobal((event.target as HTMLInputElement).value, 'customContains');
}

private configureFilter () {
    // build-in filter
    let containsFilter = this.filterService.filters['contains']; 
    let startsWithFilter = this.filterService.filters['startsWith']; 
    let endsWithFilter = this.filterService.filters['endsWith']; 

    // register  custom filter
    this.filterService.register("customContains", (value, filter): boolean => {
        if (filter === undefined || filter === null || filter.trim() === '') {
            return true;
        }
        if (value === undefined || value === null) {
            return false;
        }
        const str = filter.trim().split(" ");
        if (str.length === 2 ) {
            console.log(filter)

            return startsWithFilter(value, str[0]) &&  endsWithFilter(value, str[1]);
        } else {
            return containsFilter(value, filter); 
        }
    });
}

Escenario 2: clave de búsqueda: john man doe entradas de la tabla: john man doe han

El filtro de arriba no está funcionando.

Estoy buscando una solución que dé el resultado correcto para N número de palabras.

Respuesta #1

John Kelvin Doe

no contiene

John Doe

Contiene John y contiene Doe, pero no contiene John Doe. Si quieres encontrar entradas que contengan ambas palabras, entonces necesitarás buscar un filtro de contiene para ambas y poner un && entre ellas.

john hombre doe han

comienza con

john hombre doe

pero no termina con

john hombre doe

Por lo tanto, no es cierto que comience con john man doe Y termine con ello. Así que, en lugar de tu

        const str = filter.trim().split(" ");
        if (str.length === 2 ) {
            console.log(filter)

            return startsWithFilter(value, str[0]) &&  endsWithFilter(value, str[1]);
        } else {
            return containsFilter(value, filter); 
        }

Yo recomiendo

        const str = filter.trim().split(" ");
        for (let f of filter) {
            if (!containsFilter(value, f)) return false;
        }
        return true;

como la solución. Básicamente, dividimos el filtro por espacios y recorremos los elementos y verificamos para cada uno si están contenidos en value.

Respuesta #2

No estoy seguro si esto coincide con la última tabla de PrimeNG.

<p-table
 ...
 [globalFilterFields]="['column_name']">

  <button (click)="table.filterGlobal(['ValueOne', 'ValueTwo'], 'in')"></button>
  <button (click)="table.filterGlobal('ValueOne', 'contains')"></button>

La clave es la "restricción" in y contains. Vea las otras restricciones del servicio de filtros