Skip to content

Commit

Permalink
refactor: extract FilterSphereProvider
Browse files Browse the repository at this point in the history
  • Loading branch information
lawvs committed Aug 2, 2024
1 parent e0390ad commit 49df2cd
Show file tree
Hide file tree
Showing 8 changed files with 108 additions and 68 deletions.
14 changes: 14 additions & 0 deletions .changeset/rich-dryers-rhyme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
"@fn-sphere/filter": minor
---

Add new `FilterSphereProvider` component to provide filter context to children components.

Add `useFilterSphere` hook to access filter predicate.

The `FilterBuilder` component no longer adds a provider to its child components.

```ts
const { filterRule, schema, predicate } = useFilterSphere<YourData>();
const filteredData = data.filter(predicate);
```
55 changes: 0 additions & 55 deletions packages/filter/src/filter-builder.tsx

This file was deleted.

66 changes: 66 additions & 0 deletions packages/filter/src/filter-sphere-provider.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
import { Fragment, type PropsWithChildren } from "react";
import { FilterSchemaProvider } from "./hooks/use-filter-schema-context.js";
import {
FilterThemeProvider,
presetTheme,
type ThemeSpec,
} from "./theme/index.js";
import type { BasicFilterSphereInput } from "./types.js";

export type FilterThemeInput = {
dataInputViews?: ThemeSpec["dataInputViews"];
components?: Partial<ThemeSpec["components"]>;
primitives?: Partial<ThemeSpec["primitives"]>;
templates?: Partial<ThemeSpec["templates"]>;
};

export interface FilterSphereProviderProps<Data>
extends BasicFilterSphereInput<Data> {
theme?: FilterThemeInput;
}

export const FilterSphereProvider = <Data,>({
schema,
filterList,
filterRule,
onRuleChange,
mapFieldName,
mapFilterName,
fieldDeepLimit,
theme,
children,
}: PropsWithChildren<FilterSphereProviderProps<Data>>) => {
const MaybeThemeProviderWithChildren = theme ? (
<FilterThemeProvider
theme={{
dataInputViews: [
...(theme.dataInputViews ?? []),
...presetTheme.dataInputViews,
],
components: { ...presetTheme.components, ...theme.components },
primitives: { ...presetTheme.primitives, ...theme.primitives },
templates: { ...presetTheme.templates, ...theme.templates },
}}
>
{children}
</FilterThemeProvider>
) : (
<Fragment>{children}</Fragment>
);

return (
<FilterSchemaProvider
value={{
schema,
filterList,
filterRule,
onRuleChange,
mapFieldName,
mapFilterName,
fieldDeepLimit,
}}
>
{MaybeThemeProviderWithChildren}
</FilterSchemaProvider>
);
};
10 changes: 5 additions & 5 deletions packages/filter/src/hooks/use-filter-group.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { createFilterGroup, createSingleFilter } from "../utils.js";
import { useFilterSchemaContext } from "./use-filter-schema-context.js";

export const useFilterGroup = (ruleGroup: FilterGroup) => {
const { filterMap, onRuleChange } = useFilterSchemaContext();
const { filterMap, onFilterMapChange } = useFilterSchemaContext();
const ruleNode = filterMap[ruleGroup.id];
if (!ruleNode) {
console.error("Rule not found in filterMap", ruleGroup, filterMap);
Expand Down Expand Up @@ -33,7 +33,7 @@ export const useFilterGroup = (ruleGroup: FilterGroup) => {
if (oldOp === newOp) {
return;
}
onRuleChange({
onFilterMapChange({
...filterMap,
[ruleGroup.id]: {
...ruleNode,
Expand All @@ -46,7 +46,7 @@ export const useFilterGroup = (ruleGroup: FilterGroup) => {
newRule: SingleFilter = createSingleFilter(),
index = Infinity,
) => {
onRuleChange({
onFilterMapChange({
...filterMap,
[ruleNode.id]: {
...ruleNode,
Expand All @@ -71,7 +71,7 @@ export const useFilterGroup = (ruleGroup: FilterGroup) => {
}),
index = Infinity,
) => {
onRuleChange({
onFilterMapChange({
...filterMap,
[ruleNode.id]: {
...ruleNode,
Expand All @@ -97,7 +97,7 @@ export const useFilterGroup = (ruleGroup: FilterGroup) => {
delete newFilterMap[id];
});
delete newFilterMap[ruleNode.id];
onRuleChange(newFilterMap);
onFilterMapChange(newFilterMap);
};

return {
Expand Down
4 changes: 2 additions & 2 deletions packages/filter/src/hooks/use-filter-sphere.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ import { useFilterSchemaContext } from "./use-filter-schema-context.js";
* Must be used within a `FilterSchemaProvider` or `FilterSphereProvider` component.
*
* @example
* ```
* const { rule, schema, predicate } = useFilterSphere<YourData>();
* ```ts
* const { filterRule, schema, predicate } = useFilterSphere<YourData>();
* const filteredData = data.filter(predicate);
* ```
*/
Expand Down
11 changes: 9 additions & 2 deletions packages/filter/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,16 @@
export { FilterBuilder } from "./filter-builder.js";
export {
FilterSphereProvider,
type FilterSphereProviderProps,
type FilterThemeInput,
} from "./filter-sphere-provider.js";
export { FlattenFilterBuilder } from "./flatten-filter-builder.js";
export { useFilterGroup } from "./hooks/use-filter-group.js";
export { useFilterRule } from "./hooks/use-filter-rule.js";
export { useFilterSelect } from "./hooks/use-filter-select.js";
export { useRootRule } from "./hooks/use-root-rule.js";
export * from "./theme/index.js";
export type {
BasicFilterSphereInput,
BasicFilterSphereInput,
BasicFilterSphereProps,
} from "./types.js";
export {
Expand All @@ -15,10 +19,13 @@ export {
defaultMapFieldName,
defaultMapFilterName,
} from "./utils.js";
export { FilterBuilder } from "./views/filter-builder.js";

export {
booleanFilter,
commonFilters,
countNumberOfRules,
createFilterPredicate,
dateFilter,
genericFilter,
numberFilter,
Expand Down
8 changes: 4 additions & 4 deletions packages/filter/src/theme/context.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,14 +13,14 @@ export const useFilterTheme = () => {
};

export const FilterThemeProvider = ({
spec,
theme,
children,
}: {
spec: ThemeSpec;
children: ReactNode;
theme: ThemeSpec;
children?: ReactNode;
}) => {
return (
<FilterThemeContext.Provider value={spec}>
<FilterThemeContext.Provider value={theme}>
{children}
</FilterThemeContext.Provider>
);
Expand Down
8 changes: 8 additions & 0 deletions packages/filter/src/views/filter-builder.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import { useFilterSchemaContext } from "../hooks/use-filter-schema-context.js";
import { useView } from "../theme/hooks.js";

export const FilterBuilder = () => {
const { FilterGroup } = useView("templates");
const { filterRule } = useFilterSchemaContext();
return <FilterGroup rule={filterRule} />;
};

0 comments on commit 49df2cd

Please sign in to comment.