fix(server): preserve anyFieldFilterValue in view manifest sync (#22004)

### Summary
- Fixes #19978 
- `shouldHideEmptyGroups` was already wired up in the type and
converter; this PR only closes the remaining gap for
`anyFieldFilterValue`.

<!-- This is an auto-generated description by cubic. -->
<a
href="https://cubic.dev/pr/twentyhq/twenty/pull/22004?utm_source=github"
target="_blank" rel="noopener noreferrer"
data-no-image-dialog="true"><picture><source
media="(prefers-color-scheme: dark)"
srcset="https://www.cubic.dev/buttons/review-in-cubic-dark.svg"><source
media="(prefers-color-scheme: light)"
srcset="https://www.cubic.dev/buttons/review-in-cubic-light.svg"><img
alt="Review in cubic"
src="https://www.cubic.dev/buttons/review-in-cubic-dark.svg"></picture></a>
<!-- End of auto-generated description by cubic. -->

---------

Signed-off-by: Parship Chowdhury <parshipchowdhury@gmail.com>
Co-authored-by: Charles Bochet <charles@twenty.com>
This commit is contained in:
Parship Chowdhury
2026-06-25 21:41:35 +05:30
committed by GitHub
parent 35d64ac7f2
commit 1076866820
4 changed files with 37 additions and 1 deletions
@@ -114,6 +114,7 @@ describe('fromViewManifestToUniversalFlatView', () => {
).toBeNull();
expect(result.calendarLayout).toBeNull();
expect(result.calendarFieldMetadataUniversalIdentifier).toBeNull();
expect(result.anyFieldFilterValue).toBeNull();
});
it('should preserve calendar fields from the manifest', () => {
@@ -135,4 +136,19 @@ describe('fromViewManifestToUniversalFlatView', () => {
'field-uuid-date',
);
});
it('should preserve anyFieldFilterValue from the manifest', () => {
const result = fromViewManifestToUniversalFlatView({
viewManifest: {
universalIdentifier: 'view-uuid-6',
name: 'Filtered View',
objectUniversalIdentifier: 'object-uuid-1',
anyFieldFilterValue: 'search term',
},
applicationUniversalIdentifier,
now,
});
expect(result.anyFieldFilterValue).toBe('search term');
});
});
@@ -40,7 +40,7 @@ export const fromViewManifestToUniversalFlatView = ({
viewManifest.mainGroupByFieldMetadataUniversalIdentifier ?? null,
shouldHideEmptyGroups: viewManifest.shouldHideEmptyGroups ?? false,
kanbanColumnWidth: viewManifest.kanbanColumnWidth ?? null,
anyFieldFilterValue: null,
anyFieldFilterValue: viewManifest.anyFieldFilterValue ?? null,
createdByUserWorkspaceId: null,
isActive: true,
isSystemSideEffect: false,
@@ -25,6 +25,9 @@ const ARM_VIEW_FIELD_ID = uuidv4();
const HEAD_VIEW_FIELD_ID = uuidv4();
const TAIL_VIEW_FIELD_ID = uuidv4();
const INITIAL_ANY_FIELD_FILTER_VALUE = 'arm';
const UPDATED_ANY_FIELD_FILTER_VALUE = 'tail';
const HUMAN_OBJECT = buildDefaultObjectManifest({
nameSingular: 'human',
namePlural: 'humans',
@@ -65,6 +68,7 @@ const buildInitialManifest = (): Manifest =>
universalIdentifier: BODY_VIEW_ID,
name: 'Body',
objectUniversalIdentifier: HUMAN_OBJECT.universalIdentifier,
anyFieldFilterValue: INITIAL_ANY_FIELD_FILTER_VALUE,
fields: [
{
universalIdentifier: ARM_VIEW_FIELD_ID,
@@ -106,6 +110,7 @@ const buildResyncManifest = (): Manifest =>
universalIdentifier: BODY_VIEW_ID,
name: 'Body',
objectUniversalIdentifier: HUMAN_OBJECT.universalIdentifier,
anyFieldFilterValue: UPDATED_ANY_FIELD_FILTER_VALUE,
fields: [
{
universalIdentifier: ARM_VIEW_FIELD_ID,
@@ -179,6 +184,7 @@ describe('Successful re-sync of an application whose app-owned view references a
const bodyView = viewsData?.getViews.find((view) => view.name === 'Body');
expect(bodyView).toBeDefined();
expect(bodyView?.anyFieldFilterValue).toBe(INITIAL_ANY_FIELD_FILTER_VALUE);
const { data: createViewFieldData } = await createOneViewField({
input: {
@@ -207,6 +213,19 @@ describe('Successful re-sync of an application whose app-owned view references a
expect(tailField).toBeDefined();
const { data: viewsDataAfterResync } = await findViews({
objectMetadataId: humanObjectAfterResync?.id,
expectToFail: false,
});
const bodyViewAfterResync = viewsDataAfterResync?.getViews.find(
(view) => view.name === 'Body',
);
expect(bodyViewAfterResync?.anyFieldFilterValue).toBe(
UPDATED_ANY_FIELD_FILTER_VALUE,
);
const { data: viewFieldsData } = await findViewFields({
viewId: bodyView?.id ?? '',
expectToFail: false,
@@ -75,6 +75,7 @@ export type ViewManifest = SyncableEntityOptions & {
openRecordIn?: ViewOpenRecordIn;
mainGroupByFieldMetadataUniversalIdentifier?: string;
shouldHideEmptyGroups?: boolean;
anyFieldFilterValue?: string | null;
kanbanColumnWidth?: number | null;
kanbanAggregateOperation?: AggregateOperations;
kanbanAggregateOperationFieldMetadataUniversalIdentifier?: string;