mirror of
https://github.com/home-assistant/frontend.git
synced 2025-07-20 15:56:35 +00:00
Fix data table worker (#5921)
This commit is contained in:
parent
bbc16b6bc8
commit
d9bb40f934
@ -21,7 +21,8 @@ import { nextRender } from "../../common/util/render-status";
|
||||
import "../ha-checkbox";
|
||||
import type { HaCheckbox } from "../ha-checkbox";
|
||||
import "../ha-icon";
|
||||
import { filterSortData } from "./sort-filter";
|
||||
import { filterData, sortData } from "./sort-filter";
|
||||
import memoizeOne from "memoize-one";
|
||||
|
||||
declare global {
|
||||
// for fire event
|
||||
@ -72,6 +73,10 @@ export interface DataTableRowData {
|
||||
selectable?: boolean;
|
||||
}
|
||||
|
||||
export interface SortableColumnContainer {
|
||||
[key: string]: DataTableSortColumnData;
|
||||
}
|
||||
|
||||
@customElement("ha-data-table")
|
||||
export class HaDataTable extends LitElement {
|
||||
@property({ type: Object }) public columns: DataTableColumnContainer = {};
|
||||
@ -109,9 +114,7 @@ export class HaDataTable extends LitElement {
|
||||
|
||||
private _checkedRows: string[] = [];
|
||||
|
||||
private _sortColumns: {
|
||||
[key: string]: DataTableSortColumnData;
|
||||
} = {};
|
||||
private _sortColumns: SortableColumnContainer = {};
|
||||
|
||||
private curRequest = 0;
|
||||
|
||||
@ -179,7 +182,7 @@ export class HaDataTable extends LitElement {
|
||||
properties.has("_sortColumn") ||
|
||||
properties.has("_sortDirection")
|
||||
) {
|
||||
this._filterData();
|
||||
this._sortFilterData();
|
||||
}
|
||||
}
|
||||
|
||||
@ -369,20 +372,30 @@ export class HaDataTable extends LitElement {
|
||||
`;
|
||||
}
|
||||
|
||||
private async _filterData() {
|
||||
private async _sortFilterData() {
|
||||
const startTime = new Date().getTime();
|
||||
this.curRequest++;
|
||||
const curRequest = this.curRequest;
|
||||
|
||||
const filterProm = filterSortData(
|
||||
this.data,
|
||||
this._sortColumns,
|
||||
this._filter,
|
||||
this._sortDirection,
|
||||
this._sortColumn
|
||||
);
|
||||
let filteredData = this.data;
|
||||
if (this._filter) {
|
||||
filteredData = await this._memFilterData(
|
||||
this.data,
|
||||
this._sortColumns,
|
||||
this.filter
|
||||
);
|
||||
}
|
||||
|
||||
const [data] = await Promise.all([filterProm, nextRender]);
|
||||
const prom = this._sortColumn
|
||||
? sortData(
|
||||
filteredData,
|
||||
this._sortColumns,
|
||||
this._sortDirection,
|
||||
this._sortColumn
|
||||
)
|
||||
: filteredData;
|
||||
|
||||
const [data] = await Promise.all([prom, nextRender]);
|
||||
|
||||
const curTime = new Date().getTime();
|
||||
const elapsed = curTime - startTime;
|
||||
@ -396,6 +409,16 @@ export class HaDataTable extends LitElement {
|
||||
this._filteredData = data;
|
||||
}
|
||||
|
||||
private _memFilterData = memoizeOne(
|
||||
async (
|
||||
data: DataTableRowData[],
|
||||
columns: SortableColumnContainer,
|
||||
filter: string
|
||||
): Promise<DataTableRowData[]> => {
|
||||
return filterData(data, columns, filter);
|
||||
}
|
||||
);
|
||||
|
||||
private _handleHeaderClick(ev: Event) {
|
||||
const columnId = ((ev.target as HTMLElement).closest(
|
||||
".mdc-data-table__header-cell"
|
||||
|
@ -1,26 +1,34 @@
|
||||
import { wrap } from "comlink";
|
||||
|
||||
type FilterSortDataType = typeof import("./sort_filter_worker").api["filterSortData"];
|
||||
type filterSortDataParamTypes = Parameters<FilterSortDataType>;
|
||||
type FilterDataType = typeof import("./sort_filter_worker").api["filterData"];
|
||||
type FilterDataParamTypes = Parameters<FilterDataType>;
|
||||
|
||||
type SortDataType = typeof import("./sort_filter_worker").api["sortData"];
|
||||
type SortDataParamTypes = Parameters<SortDataType>;
|
||||
|
||||
let worker: any | undefined;
|
||||
|
||||
export const filterSortData = async (
|
||||
data: filterSortDataParamTypes[0],
|
||||
columns: filterSortDataParamTypes[1],
|
||||
filter: filterSortDataParamTypes[2],
|
||||
direction: filterSortDataParamTypes[3],
|
||||
sortColumn: filterSortDataParamTypes[4]
|
||||
): Promise<ReturnType<FilterSortDataType>> => {
|
||||
export const filterData = async (
|
||||
data: FilterDataParamTypes[0],
|
||||
columns: FilterDataParamTypes[1],
|
||||
filter: FilterDataParamTypes[2]
|
||||
): Promise<ReturnType<FilterDataType>> => {
|
||||
if (!worker) {
|
||||
worker = wrap(new Worker("./sort_filter_worker", { type: "module" }));
|
||||
}
|
||||
|
||||
return await worker.filterSortData(
|
||||
data,
|
||||
columns,
|
||||
filter,
|
||||
direction,
|
||||
sortColumn
|
||||
);
|
||||
return await worker.filterData(data, columns, filter);
|
||||
};
|
||||
|
||||
export const sortData = async (
|
||||
data: SortDataParamTypes[0],
|
||||
columns: SortDataParamTypes[1],
|
||||
direction: SortDataParamTypes[2],
|
||||
sortColumn: SortDataParamTypes[3]
|
||||
): Promise<ReturnType<SortDataType>> => {
|
||||
if (!worker) {
|
||||
worker = wrap(new Worker("./sort_filter_worker", { type: "module" }));
|
||||
}
|
||||
|
||||
return await worker.sortData(data, columns, direction, sortColumn);
|
||||
};
|
||||
|
@ -5,33 +5,16 @@ import type {
|
||||
DataTableSortColumnData,
|
||||
DataTableRowData,
|
||||
SortingDirection,
|
||||
HaDataTable,
|
||||
SortableColumnContainer,
|
||||
} from "./ha-data-table";
|
||||
|
||||
type SortableColumnContainer = HaDataTable["_sortColumns"];
|
||||
|
||||
const filterSortData = (
|
||||
data: DataTableRowData[],
|
||||
columns: SortableColumnContainer,
|
||||
filter: string,
|
||||
direction: SortingDirection,
|
||||
sortColumn?: string
|
||||
) => {
|
||||
const filteredData = filter ? filterData(data, columns, filter) : data;
|
||||
|
||||
if (!sortColumn) {
|
||||
return filteredData;
|
||||
}
|
||||
|
||||
return sortData(filteredData, columns, direction, sortColumn);
|
||||
};
|
||||
|
||||
const filterData = (
|
||||
data: DataTableRowData[],
|
||||
columns: SortableColumnContainer,
|
||||
filter: string
|
||||
) =>
|
||||
data.filter((row) => {
|
||||
) => {
|
||||
filter = filter.toUpperCase();
|
||||
return data.filter((row) => {
|
||||
return Object.entries(columns).some((columnEntry) => {
|
||||
const [key, column] = columnEntry;
|
||||
if (column.filterable) {
|
||||
@ -46,6 +29,7 @@ const filterData = (
|
||||
return false;
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
const sortData = (
|
||||
data: DataTableRowData[],
|
||||
@ -85,7 +69,8 @@ const sortData = (
|
||||
|
||||
// Export for types
|
||||
export const api = {
|
||||
filterSortData,
|
||||
filterData,
|
||||
sortData,
|
||||
};
|
||||
|
||||
expose(api);
|
||||
|
Loading…
x
Reference in New Issue
Block a user