fix: workspace member "me" filters now work in dashboard widgets (#20266)
## Summary Fixes #20225 Dashboard graph widgets only passed `timeZone` in `filterValueDependencies` when computing the GraphQL operation filter. As a result, `isCurrentWorkspaceMemberSelected` ("me") filters were silently ignored — the current workspace member ID was `undefined`. Regular view filters already use `useFilterValueDependencies` which provides both `timeZone` and `currentWorkspaceMemberId`. This PR replaces the manual `{ timeZone: userTimezone }` object in `useGraphWidgetQueryCommon` with `useFilterValueDependencies()`, giving dashboard widgets full feature parity with view filters. **Changed file:** `packages/twenty-front/src/modules/page-layout/widgets/graph/hooks/useGraphWidgetQueryCommon.ts` --------- Co-authored-by: martmull <[email protected]> Co-authored-by: Claude Opus 4.6 (1M context) <[email protected]>
This commit is contained in:
co-authored by
martmull
Claude Opus 4.6
parent
2eae25dc34
commit
2b4fa9d8cf
+3
-5
@@ -1,5 +1,5 @@
|
||||
import { useObjectMetadataItemById } from '@/object-metadata/hooks/useObjectMetadataItemById';
|
||||
import { useUserTimezone } from '@/ui/input/components/internal/date/hooks/useUserTimezone';
|
||||
import { useFilterValueDependencies } from '@/object-record/record-filter/hooks/useFilterValueDependencies';
|
||||
import {
|
||||
computeRecordGqlOperationFilter,
|
||||
isDefined,
|
||||
@@ -36,13 +36,11 @@ export const useGraphWidgetQueryCommon = ({
|
||||
throw new Error('Aggregate field not found');
|
||||
}
|
||||
|
||||
const { userTimezone } = useUserTimezone();
|
||||
const { filterValueDependencies } = useFilterValueDependencies();
|
||||
|
||||
const gqlOperationFilter = computeRecordGqlOperationFilter({
|
||||
fields: objectMetadataItem.fields,
|
||||
filterValueDependencies: {
|
||||
timeZone: userTimezone,
|
||||
},
|
||||
filterValueDependencies,
|
||||
recordFilters: configuration.filter?.recordFilters ?? [],
|
||||
recordFilterGroups: configuration.filter?.recordFilterGroups ?? [],
|
||||
});
|
||||
|
||||
+8
-1
@@ -1,4 +1,5 @@
|
||||
import { useApolloCoreClient } from '@/object-metadata/hooks/useApolloCoreClient';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
import { useMutation } from '@apollo/client/react';
|
||||
import {
|
||||
type CreateWorkflowVersionEdgeMutation,
|
||||
@@ -12,6 +13,7 @@ export const useCreateWorkflowVersionEdge = () => {
|
||||
const apolloCoreClient = useApolloCoreClient();
|
||||
|
||||
const { updateWorkflowVersionCache } = useUpdateWorkflowVersionCache();
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const [mutate] = useMutation<
|
||||
CreateWorkflowVersionEdgeMutation,
|
||||
@@ -21,7 +23,12 @@ export const useCreateWorkflowVersionEdge = () => {
|
||||
const createWorkflowVersionEdge = async (
|
||||
input: CreateWorkflowVersionEdgeInput,
|
||||
) => {
|
||||
const result = await mutate({ variables: { input } });
|
||||
const result = await mutate({
|
||||
variables: { input },
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
|
||||
const workflowVersionStepChanges = result?.data?.createWorkflowVersionEdge;
|
||||
|
||||
|
||||
+5
@@ -1,5 +1,6 @@
|
||||
import { useApolloCoreClient } from '@/object-metadata/hooks/useApolloCoreClient';
|
||||
import { CREATE_WORKFLOW_VERSION_STEP } from '@/workflow/graphql/mutations/createWorkflowVersionStep';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
import { useMutation } from '@apollo/client/react';
|
||||
import {
|
||||
type CreateWorkflowVersionStepInput,
|
||||
@@ -17,6 +18,7 @@ export const useCreateWorkflowVersionStep = () => {
|
||||
const { updateWorkflowVersionCache } = useUpdateWorkflowVersionCache();
|
||||
|
||||
const setFlow = useSetAtomComponentState(flowComponentState);
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const [mutate] = useMutation<
|
||||
CreateWorkflowVersionStepMutation,
|
||||
@@ -30,6 +32,9 @@ export const useCreateWorkflowVersionStep = () => {
|
||||
) => {
|
||||
const result = await mutate({
|
||||
variables: { input },
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
|
||||
const workflowVersionStepChanges = result?.data?.createWorkflowVersionStep;
|
||||
|
||||
+5
@@ -3,6 +3,7 @@ import { CoreObjectNameSingular } from 'twenty-shared/types';
|
||||
import { useFindOneRecordQuery } from '@/object-record/hooks/useFindOneRecordQuery';
|
||||
import { DELETE_WORKFLOW_VERSION_STEP } from '@/workflow/graphql/mutations/deleteWorkflowVersionStep';
|
||||
import { useUpdateWorkflowVersionCache } from '@/workflow/workflow-steps/hooks/useUpdateWorkflowVersionCache';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
import { useMutation } from '@apollo/client/react';
|
||||
import {
|
||||
type DeleteWorkflowVersionStepInput,
|
||||
@@ -14,6 +15,7 @@ export const useDeleteWorkflowVersionStep = () => {
|
||||
const apolloCoreClient = useApolloCoreClient();
|
||||
|
||||
const { updateWorkflowVersionCache } = useUpdateWorkflowVersionCache();
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const { findOneRecordQuery: findOneWorkflowVersionQuery } =
|
||||
useFindOneRecordQuery({
|
||||
@@ -39,6 +41,9 @@ export const useDeleteWorkflowVersionStep = () => {
|
||||
variables: { objectRecordId: input.workflowVersionId },
|
||||
},
|
||||
],
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
|
||||
const workflowVersionStepChanges = result?.data?.deleteWorkflowVersionStep;
|
||||
|
||||
+5
@@ -3,6 +3,7 @@ import { useSetAtomComponentState } from '@/ui/utilities/state/jotai/hooks/useSe
|
||||
import { DUPLICATE_WORKFLOW_VERSION_STEP } from '@/workflow/graphql/mutations/duplicateWorkflowVersionStep';
|
||||
import { flowComponentState } from '@/workflow/states/flowComponentState';
|
||||
import { useUpdateWorkflowVersionCache } from '@/workflow/workflow-steps/hooks/useUpdateWorkflowVersionCache';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
import { useMutation } from '@apollo/client/react';
|
||||
import { isDefined } from 'twenty-shared/utils';
|
||||
import {
|
||||
@@ -17,6 +18,7 @@ export const useDuplicateWorkflowVersionStep = () => {
|
||||
const { updateWorkflowVersionCache } = useUpdateWorkflowVersionCache();
|
||||
|
||||
const setFlow = useSetAtomComponentState(flowComponentState);
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const [mutate] = useMutation<
|
||||
DuplicateWorkflowVersionStepMutation,
|
||||
@@ -30,6 +32,9 @@ export const useDuplicateWorkflowVersionStep = () => {
|
||||
) => {
|
||||
const result = await mutate({
|
||||
variables: { input },
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
|
||||
const workflowVersionStepChanges =
|
||||
|
||||
+5
@@ -7,6 +7,7 @@ import { updateRecordFromCache } from '@/object-record/cache/utils/updateRecordF
|
||||
import { useObjectPermissions } from '@/object-record/hooks/useObjectPermissions';
|
||||
import { UPDATE_WORKFLOW_RUN_STEP } from '@/workflow/graphql/mutations/updateWorkflowRunStep';
|
||||
import { type WorkflowStep, type WorkflowRun } from '@/workflow/types/Workflow';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
import { useMutation } from '@apollo/client/react';
|
||||
import { isDefined } from 'twenty-shared/utils';
|
||||
import {
|
||||
@@ -32,12 +33,16 @@ export const useUpdateWorkflowRunStep = () => {
|
||||
const getRecordFromCache = useGetRecordFromCache({
|
||||
objectNameSingular: CoreObjectNameSingular.WorkflowRun,
|
||||
});
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const updateWorkflowRunStep = async (input: UpdateWorkflowRunStepInput) => {
|
||||
const result = await mutate({
|
||||
variables: {
|
||||
input: { workflowRunId: input.workflowRunId, step: input.step },
|
||||
},
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
const updatedStep = result?.data?.updateWorkflowRunStep;
|
||||
if (!isDefined(updatedStep)) {
|
||||
|
||||
+8
-1
@@ -10,6 +10,7 @@ import {
|
||||
type WorkflowVersion,
|
||||
type WorkflowStep,
|
||||
} from '@/workflow/types/Workflow';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
import { useMutation } from '@apollo/client/react';
|
||||
import { isDefined } from 'twenty-shared/utils';
|
||||
import {
|
||||
@@ -22,6 +23,7 @@ export const useUpdateWorkflowVersionStep = () => {
|
||||
const apolloCoreClient = useApolloCoreClient();
|
||||
const { objectMetadataItems } = useObjectMetadataItems();
|
||||
const { objectPermissionsByObjectMetadataId } = useObjectPermissions();
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const { objectMetadataItem } = useObjectMetadataItem({
|
||||
objectNameSingular: CoreObjectNameSingular.WorkflowVersion,
|
||||
@@ -39,7 +41,12 @@ export const useUpdateWorkflowVersionStep = () => {
|
||||
const updateWorkflowVersionStep = async (
|
||||
input: UpdateWorkflowVersionStepInput,
|
||||
) => {
|
||||
const result = await mutate({ variables: { input } });
|
||||
const result = await mutate({
|
||||
variables: { input },
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
const updatedStep = result?.data?.updateWorkflowVersionStep;
|
||||
if (!isDefined(updatedStep)) {
|
||||
return;
|
||||
|
||||
+2
@@ -4,6 +4,7 @@ import { type Meta, type StoryObj } from '@storybook/react-vite';
|
||||
import { fn } from 'storybook/test';
|
||||
import { StepLogicalOperator, ViewFilterOperand } from 'twenty-shared/types';
|
||||
import { ComponentDecorator, RouterDecorator } from 'twenty-ui/testing';
|
||||
import { SnackBarDecorator } from '~/testing/decorators/SnackBarDecorator';
|
||||
import { WorkflowStepActionDrawerDecorator } from '~/testing/decorators/WorkflowStepActionDrawerDecorator';
|
||||
import { WorkflowStepDecorator } from '~/testing/decorators/WorkflowStepDecorator';
|
||||
import { WorkspaceDecorator } from '~/testing/decorators/WorkspaceDecorator';
|
||||
@@ -87,6 +88,7 @@ const meta: Meta<typeof WorkflowEditActionFilter> = {
|
||||
ComponentDecorator,
|
||||
RouterDecorator,
|
||||
WorkspaceDecorator,
|
||||
SnackBarDecorator,
|
||||
],
|
||||
};
|
||||
|
||||
|
||||
+2
@@ -5,6 +5,7 @@ import { expect, fn, userEvent, waitFor, within } from 'storybook/test';
|
||||
import { FieldMetadataType } from 'twenty-shared/types';
|
||||
import { ComponentDecorator, RouterDecorator } from 'twenty-ui/testing';
|
||||
import { ObjectMetadataItemsDecorator } from '~/testing/decorators/ObjectMetadataItemsDecorator';
|
||||
import { SnackBarDecorator } from '~/testing/decorators/SnackBarDecorator';
|
||||
import { WorkflowStepActionDrawerDecorator } from '~/testing/decorators/WorkflowStepActionDrawerDecorator';
|
||||
import { WorkflowStepDecorator } from '~/testing/decorators/WorkflowStepDecorator';
|
||||
import { graphqlMocks } from '~/testing/graphqlMocks';
|
||||
@@ -61,6 +62,7 @@ const meta: Meta<typeof WorkflowEditActionFormBuilder> = {
|
||||
ComponentDecorator,
|
||||
RouterDecorator,
|
||||
ObjectMetadataItemsDecorator,
|
||||
SnackBarDecorator,
|
||||
],
|
||||
};
|
||||
|
||||
|
||||
+2
@@ -30,6 +30,7 @@ describe('useCreateWorkspaceInvitation', () => {
|
||||
|
||||
expect(mutationCallSpy).toHaveBeenCalledWith({
|
||||
onCompleted: expect.any(Function),
|
||||
onError: expect.any(Function),
|
||||
variables: params,
|
||||
});
|
||||
});
|
||||
@@ -46,6 +47,7 @@ describe('useCreateWorkspaceInvitation', () => {
|
||||
|
||||
expect(mutationCallSpy).toHaveBeenCalledWith({
|
||||
onCompleted: expect.any(Function),
|
||||
onError: expect.any(Function),
|
||||
variables: params,
|
||||
});
|
||||
});
|
||||
|
||||
+1
@@ -30,6 +30,7 @@ describe('useDeleteWorkspaceInvitation', () => {
|
||||
|
||||
expect(mutationCallSpy).toHaveBeenCalledWith({
|
||||
onCompleted: expect.any(Function),
|
||||
onError: expect.any(Function),
|
||||
variables: params,
|
||||
});
|
||||
});
|
||||
|
||||
+1
@@ -30,6 +30,7 @@ describe('useResendWorkspaceInvitation', () => {
|
||||
|
||||
expect(mutationCallSpy).toHaveBeenCalledWith({
|
||||
onCompleted: expect.any(Function),
|
||||
onError: expect.any(Function),
|
||||
variables: params,
|
||||
});
|
||||
});
|
||||
|
||||
+5
@@ -5,11 +5,13 @@ import {
|
||||
} from '~/generated-metadata/graphql';
|
||||
import { workspaceInvitationsState } from '@/workspace-invitation/states/workspaceInvitationsStates';
|
||||
import { useSetAtomState } from '@/ui/utilities/state/jotai/hooks/useSetAtomState';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
|
||||
export const useCreateWorkspaceInvitation = () => {
|
||||
const [sendInvitationsMutation] = useMutation(SendInvitationsDocument);
|
||||
|
||||
const setWorkspaceInvitations = useSetAtomState(workspaceInvitationsState);
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const sendInvitation = async (
|
||||
variables: SendInvitationsMutationVariables,
|
||||
@@ -22,6 +24,9 @@ export const useCreateWorkspaceInvitation = () => {
|
||||
...data.sendInvitations.result,
|
||||
]);
|
||||
},
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
+5
@@ -5,6 +5,7 @@ import {
|
||||
} from '~/generated-metadata/graphql';
|
||||
import { workspaceInvitationsState } from '@/workspace-invitation/states/workspaceInvitationsStates';
|
||||
import { useSetAtomState } from '@/ui/utilities/state/jotai/hooks/useSetAtomState';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
|
||||
export const useDeleteWorkspaceInvitation = () => {
|
||||
const [deleteWorkspaceInvitationMutation] = useMutation(
|
||||
@@ -12,6 +13,7 @@ export const useDeleteWorkspaceInvitation = () => {
|
||||
);
|
||||
|
||||
const setWorkspaceInvitations = useSetAtomState(workspaceInvitationsState);
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const deleteWorkspaceInvitation = async ({
|
||||
appTokenId,
|
||||
@@ -27,6 +29,9 @@ export const useDeleteWorkspaceInvitation = () => {
|
||||
),
|
||||
);
|
||||
},
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
+5
@@ -5,6 +5,7 @@ import {
|
||||
} from '~/generated-metadata/graphql';
|
||||
import { workspaceInvitationsState } from '@/workspace-invitation/states/workspaceInvitationsStates';
|
||||
import { useSetAtomState } from '@/ui/utilities/state/jotai/hooks/useSetAtomState';
|
||||
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
|
||||
|
||||
export const useResendWorkspaceInvitation = () => {
|
||||
const [resendWorkspaceInvitationMutation] = useMutation(
|
||||
@@ -12,6 +13,7 @@ export const useResendWorkspaceInvitation = () => {
|
||||
);
|
||||
|
||||
const setWorkspaceInvitations = useSetAtomState(workspaceInvitationsState);
|
||||
const { enqueueErrorSnackBar } = useSnackBar();
|
||||
|
||||
const resendInvitation = async ({
|
||||
appTokenId,
|
||||
@@ -28,6 +30,9 @@ export const useResendWorkspaceInvitation = () => {
|
||||
),
|
||||
]);
|
||||
},
|
||||
onError: (error) => {
|
||||
enqueueErrorSnackBar({ apolloError: error });
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user