diff --git a/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx b/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx
index 8928c2b2bd..dfe7851d13 100644
--- a/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx
+++ b/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx
@@ -19,6 +19,7 @@ import { useResetTableRowSelection } from '@/object-record/record-table/hooks/in
import { useActiveRecordTableRow } from '@/object-record/record-table/hooks/useActiveRecordTableRow';
import { useFocusedRecordTableRow } from '@/object-record/record-table/hooks/useFocusedRecordTableRow';
import { useOpenNewRecordTitleCell } from '@/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell';
+import { newRecordTitleCellToOpenState } from '@/object-record/record-title-cell/states/newRecordTitleCellToOpenState';
import { getRecordIndexIdFromObjectNamePluralAndViewId } from '@/object-record/utils/getRecordIndexIdFromObjectNamePluralAndViewId';
import { PageFocusId } from '@/types/PageFocusId';
import { useResetFocusStackToFocusItem } from '@/ui/utilities/focus/hooks/useResetFocusStackToFocusItem';
@@ -206,7 +207,6 @@ export const PageChangeEffect = () => {
break;
}
case isMatchingLocation(location, AppPath.RecordShowPage): {
- const isNewRecord = location.state?.isNewRecord === true;
const isSidePanelOpen = store.get(isSidePanelOpenedState.atom);
if (!isSidePanelOpen) {
@@ -225,14 +225,21 @@ export const PageChangeEffect = () => {
});
}
- if (
- isNewRecord &&
- isDefined(location.state?.labelIdentifierFieldName)
- ) {
- openNewRecordTitleCell({
- recordId: location.state.objectRecordId,
- fieldName: location.state.labelIdentifierFieldName,
- });
+ const newRecordTitleCellToOpen = store.get(
+ newRecordTitleCellToOpenState.atom,
+ );
+
+ if (isDefined(newRecordTitleCellToOpen)) {
+ const objectRecordIdFromPath = matchPath(
+ AppPath.RecordShowPage,
+ location.pathname,
+ )?.params.objectRecordId;
+
+ if (newRecordTitleCellToOpen.recordId === objectRecordIdFromPath) {
+ openNewRecordTitleCell(newRecordTitleCellToOpen);
+ }
+
+ store.set(newRecordTitleCellToOpenState.atom, null);
}
break;
}
diff --git a/packages/twenty-front/src/modules/command-menu-item/engine-command/global/components/ComposeCampaignCommand.tsx b/packages/twenty-front/src/modules/command-menu-item/engine-command/global/components/ComposeCampaignCommand.tsx
index d6b821f056..350dee9170 100644
--- a/packages/twenty-front/src/modules/command-menu-item/engine-command/global/components/ComposeCampaignCommand.tsx
+++ b/packages/twenty-front/src/modules/command-menu-item/engine-command/global/components/ComposeCampaignCommand.tsx
@@ -17,15 +17,10 @@ export const ComposeCampaignCommand = () => {
await createMessageCampaign({ id: campaignId });
- navigateApp(
- AppPath.RecordShowPage,
- {
- objectNameSingular: CoreObjectNameSingular.MessageCampaign,
- objectRecordId: campaignId,
- },
- undefined,
- { state: { isNewRecord: true, objectRecordId: campaignId } },
- );
+ navigateApp(AppPath.RecordShowPage, {
+ objectNameSingular: CoreObjectNameSingular.MessageCampaign,
+ objectRecordId: campaignId,
+ });
};
return ;
diff --git a/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts b/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts
index b2c3e79807..a2857b9112 100644
--- a/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts
+++ b/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts
@@ -9,6 +9,7 @@ import { useResolveOpenRecordIn } from '@/object-record/record-index/hooks/useRe
import { recordIndexRecordIdsByGroupComponentFamilyState } from '@/object-record/record-index/states/recordIndexRecordIdsByGroupComponentFamilyState';
import { useUpsertRecordsInStore } from '@/object-record/record-store/hooks/useUpsertRecordsInStore';
import { useBuildRecordInputFromFilters } from '@/object-record/record-table/hooks/useBuildRecordInputFromFilters';
+import { newRecordTitleCellToOpenState } from '@/object-record/record-title-cell/states/newRecordTitleCellToOpenState';
import { type ObjectRecord } from '@/object-record/types/ObjectRecord';
import { useOpenRecordInSidePanel } from '@/side-panel/hooks/useOpenRecordInSidePanel';
import { useSidePanelMenu } from '@/side-panel/hooks/useSidePanelMenu';
@@ -101,22 +102,18 @@ export const useCreateNewIndexRecord = ({
const labelIdentifierFieldMetadataItem =
getLabelIdentifierFieldMetadataItem(objectMetadataItem);
+ if (isDefined(labelIdentifierFieldMetadataItem)) {
+ store.set(newRecordTitleCellToOpenState.atom, {
+ recordId,
+ fieldName: labelIdentifierFieldMetadataItem.name,
+ });
+ }
+
closeSidePanelMenu();
- navigate(
- AppPath.RecordShowPage,
- {
- objectNameSingular: objectMetadataItem.nameSingular,
- objectRecordId: recordId,
- },
- undefined,
- {
- state: {
- isNewRecord: true,
- objectRecordId: recordId,
- labelIdentifierFieldName: labelIdentifierFieldMetadataItem?.name,
- },
- },
- );
+ navigate(AppPath.RecordShowPage, {
+ objectNameSingular: objectMetadataItem.nameSingular,
+ objectRecordId: recordId,
+ });
}
if (isDefined(recordIndexGroupFieldMetadataItem)) {
diff --git a/packages/twenty-front/src/modules/object-record/record-title-cell/states/newRecordTitleCellToOpenState.ts b/packages/twenty-front/src/modules/object-record/record-title-cell/states/newRecordTitleCellToOpenState.ts
new file mode 100644
index 0000000000..75246a0b96
--- /dev/null
+++ b/packages/twenty-front/src/modules/object-record/record-title-cell/states/newRecordTitleCellToOpenState.ts
@@ -0,0 +1,8 @@
+import { type NewRecordTitleCellToOpen } from '@/object-record/record-title-cell/types/NewRecordTitleCellToOpen';
+import { createAtomState } from '@/ui/utilities/state/jotai/utils/createAtomState';
+
+export const newRecordTitleCellToOpenState =
+ createAtomState({
+ key: 'record-title-cell/newRecordTitleCellToOpenState',
+ defaultValue: null,
+ });
diff --git a/packages/twenty-front/src/modules/object-record/record-title-cell/types/NewRecordTitleCellToOpen.ts b/packages/twenty-front/src/modules/object-record/record-title-cell/types/NewRecordTitleCellToOpen.ts
new file mode 100644
index 0000000000..a0c5449528
--- /dev/null
+++ b/packages/twenty-front/src/modules/object-record/record-title-cell/types/NewRecordTitleCellToOpen.ts
@@ -0,0 +1,4 @@
+export type NewRecordTitleCellToOpen = {
+ recordId: string;
+ fieldName: string;
+};
diff --git a/packages/twenty-front/src/modules/side-panel/hooks/__tests__/useOpenRecordInSidePanel.test.tsx b/packages/twenty-front/src/modules/side-panel/hooks/__tests__/useOpenRecordInSidePanel.test.tsx
index f28d91b77d..ad02975faa 100644
--- a/packages/twenty-front/src/modules/side-panel/hooks/__tests__/useOpenRecordInSidePanel.test.tsx
+++ b/packages/twenty-front/src/modules/side-panel/hooks/__tests__/useOpenRecordInSidePanel.test.tsx
@@ -7,6 +7,7 @@ import { contextStoreNumberOfSelectedRecordsComponentState } from '@/context-sto
import { contextStoreTargetedRecordsRuleComponentState } from '@/context-store/states/contextStoreTargetedRecordsRuleComponentState';
import { ContextStoreViewType } from '@/context-store/types/ContextStoreViewType';
import { getLabelIdentifierFieldMetadataItem } from '@/object-metadata/utils/getLabelIdentifierFieldMetadataItem';
+import { newRecordTitleCellToOpenState } from '@/object-record/record-title-cell/states/newRecordTitleCellToOpenState';
import { getDefaultRecordPageLayoutId } from '@/page-layout/utils/getDefaultRecordPageLayoutId';
import { getTabListInstanceIdFromPageLayoutAndRecord } from '@/page-layout/utils/getTabListInstanceIdFromPageLayoutAndRecord';
import { SIDE_PANEL_COMPONENT_INSTANCE_ID } from '@/side-panel/constants/SidePanelComponentInstanceId';
@@ -133,6 +134,7 @@ describe('useOpenRecordInSidePanel', () => {
beforeEach(() => {
jest.clearAllMocks();
mockIsMobile = false;
+ jotaiStore.set(newRecordTitleCellToOpenState.atom, null);
});
it('should set the correct states and navigate to the record page', () => {
@@ -284,13 +286,12 @@ describe('useOpenRecordInSidePanel', () => {
});
});
- expect(mockNavigateApp).toHaveBeenCalledWith(
- AppPath.RecordShowPage,
- { objectNameSingular: 'person', objectRecordId: 'record-123' },
- undefined,
- undefined,
- );
+ expect(mockNavigateApp).toHaveBeenCalledWith(AppPath.RecordShowPage, {
+ objectNameSingular: 'person',
+ objectRecordId: 'record-123',
+ });
expect(mockNavigateSidePanel).not.toHaveBeenCalled();
+ expect(jotaiStore.get(newRecordTitleCellToOpenState.atom)).toBeNull();
});
it('should forward new record state to the record page on mobile', () => {
@@ -305,20 +306,16 @@ describe('useOpenRecordInSidePanel', () => {
});
});
- expect(mockNavigateApp).toHaveBeenCalledWith(
- AppPath.RecordShowPage,
- { objectNameSingular: 'person', objectRecordId: 'new-record-123' },
- undefined,
- {
- state: {
- isNewRecord: true,
- objectRecordId: 'new-record-123',
- labelIdentifierFieldName: getLabelIdentifierFieldMetadataItem(
- personMockObjectMetadataItem,
- )?.name,
- },
- },
- );
+ expect(mockNavigateApp).toHaveBeenCalledWith(AppPath.RecordShowPage, {
+ objectNameSingular: 'person',
+ objectRecordId: 'new-record-123',
+ });
+ expect(jotaiStore.get(newRecordTitleCellToOpenState.atom)).toEqual({
+ recordId: 'new-record-123',
+ fieldName: getLabelIdentifierFieldMetadataItem(
+ personMockObjectMetadataItem,
+ )?.name,
+ });
expect(mockOpenNewRecordTitleCell).not.toHaveBeenCalled();
});
diff --git a/packages/twenty-front/src/modules/side-panel/hooks/useOpenRecordInSidePanel.ts b/packages/twenty-front/src/modules/side-panel/hooks/useOpenRecordInSidePanel.ts
index 9c170a01f9..eef22005d7 100644
--- a/packages/twenty-front/src/modules/side-panel/hooks/useOpenRecordInSidePanel.ts
+++ b/packages/twenty-front/src/modules/side-panel/hooks/useOpenRecordInSidePanel.ts
@@ -14,6 +14,7 @@ import { getIconColorForObjectType } from '@/object-metadata/utils/getIconColorF
import { getLabelIdentifierFieldMetadataItem } from '@/object-metadata/utils/getLabelIdentifierFieldMetadataItem';
import { viewableRecordIdState } from '@/object-record/record-side-panel/states/viewableRecordIdState';
import { useOpenNewRecordTitleCell } from '@/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell';
+import { newRecordTitleCellToOpenState } from '@/object-record/record-title-cell/states/newRecordTitleCellToOpenState';
import { setRecordPageActiveTabId } from '@/page-layout/utils/setRecordPageActiveTabId';
import {
AppPath,
@@ -79,22 +80,19 @@ export const useOpenRecordInSidePanel = () => {
? getLabelIdentifierFieldMetadataItem(objectMetadataItemForRecordPage)
: undefined;
+ if (isNewRecord && isDefined(labelIdentifierField)) {
+ store.set(newRecordTitleCellToOpenState.atom, {
+ recordId,
+ fieldName: labelIdentifierField.name,
+ });
+ }
+
closeSidePanelMenu();
- navigate(
- AppPath.RecordShowPage,
- { objectNameSingular, objectRecordId: recordId },
- undefined,
- isNewRecord
- ? {
- state: {
- isNewRecord: true,
- objectRecordId: recordId,
- labelIdentifierFieldName: labelIdentifierField?.name,
- },
- }
- : undefined,
- );
+ navigate(AppPath.RecordShowPage, {
+ objectNameSingular,
+ objectRecordId: recordId,
+ });
return;
}