@salesforce/webapp-template-app-react-sample-b2x-experimental 1.112.7 → 1.112.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (138) hide show
  1. package/dist/CHANGELOG.md +19 -0
  2. package/dist/force-app/main/default/webapplications/appreactsampleb2x/package.json +6 -5
  3. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/graphql-operations-types.ts +12058 -214
  4. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/graphqlClient.ts +18 -15
  5. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/{propertyListingGraphQL.ts → properties/propertyListingGraphQL.ts} +1 -1
  6. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/appLayout.tsx +4 -2
  7. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{TopBar.tsx → layout/TopBar.tsx} +2 -2
  8. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{MaintenanceRequestList.tsx → maintenanceRequests/MaintenanceRequestList.tsx} +4 -4
  9. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{MaintenanceRequestListItem.tsx → maintenanceRequests/MaintenanceRequestListItem.tsx} +3 -3
  10. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/maintenanceRequests/MaintenanceSummaryDetailsModal.tsx +87 -0
  11. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{PropertyListingCard.tsx → properties/PropertyListingCard.tsx} +1 -1
  12. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/{features/global-search/components/search/SearchPagination.tsx → components/properties/PropertyListingSearchPagination.tsx} +20 -28
  13. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/constants/propertyListing.ts +4 -0
  14. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/api/accountSearchService.ts +46 -0
  15. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/api/query/distinctAccountIndustries.graphql +19 -0
  16. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/api/query/distinctAccountTypes.graphql +19 -0
  17. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/api/query/getAccountDetail.graphql +121 -0
  18. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/api/query/searchAccounts.graphql +51 -0
  19. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/pages/AccountObjectDetailPage.tsx +357 -0
  20. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/pages/AccountSearch.tsx +303 -0
  21. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/__examples__/pages/Home.tsx +34 -0
  22. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/api/objectSearchService.ts +84 -0
  23. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/ActiveFilters.tsx +89 -0
  24. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/FilterContext.tsx +73 -0
  25. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/ObjectBreadcrumb.tsx +66 -0
  26. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/PaginationControls.tsx +109 -0
  27. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/SearchBar.tsx +41 -0
  28. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/SortControl.tsx +143 -0
  29. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/BooleanFilter.tsx +74 -0
  30. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/DateFilter.tsx +121 -0
  31. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/DateRangeFilter.tsx +69 -0
  32. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/MultiSelectFilter.tsx +98 -0
  33. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/NumericRangeFilter.tsx +85 -0
  34. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/SearchFilter.tsx +37 -0
  35. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/SelectFilter.tsx +93 -0
  36. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/components/filters/TextFilter.tsx +74 -0
  37. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/hooks/useAsyncData.ts +54 -0
  38. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/hooks/useCachedAsyncData.ts +184 -0
  39. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/hooks/useObjectSearchParams.ts +247 -0
  40. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/utils/debounce.ts +22 -0
  41. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/utils/fieldUtils.ts +29 -0
  42. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/utils/filterUtils.ts +372 -0
  43. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/object-search/utils/sortUtils.ts +38 -0
  44. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/useMaintenanceRequests.ts +1 -1
  45. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyAddresses.ts +2 -2
  46. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyDetail.ts +1 -1
  47. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyListingAmenities.ts +2 -2
  48. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyListingSearch.ts +2 -2
  49. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyMapMarkers.ts +3 -3
  50. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyPrimaryImages.ts +2 -2
  51. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Application.tsx +3 -3
  52. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Dashboard.tsx +2 -2
  53. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Home.tsx +4 -2
  54. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Maintenance.tsx +2 -2
  55. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/PropertyDetails.tsx +1 -1
  56. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/PropertySearch.tsx +12 -10
  57. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/routes.tsx +6 -18
  58. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/utils/propertyListingPaginationUtils.ts +18 -0
  59. package/dist/package-lock.json +2 -2
  60. package/dist/package.json +1 -1
  61. package/dist/scripts/graphql-search.sh +69 -17
  62. package/package.json +1 -1
  63. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/MaintenanceDetailsModal.tsx +0 -128
  64. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/api/objectDetailService.ts +0 -102
  65. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/api/objectInfoGraphQLService.ts +0 -137
  66. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/api/objectInfoService.ts +0 -95
  67. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/api/recordListGraphQLService.ts +0 -364
  68. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/DetailFields.tsx +0 -55
  69. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/DetailForm.tsx +0 -146
  70. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/DetailHeader.tsx +0 -34
  71. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/DetailLayoutSections.tsx +0 -80
  72. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/Section.tsx +0 -108
  73. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/SectionRow.tsx +0 -20
  74. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/UiApiDetailForm.tsx +0 -140
  75. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/formatted/FieldValueDisplay.tsx +0 -73
  76. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/formatted/FormattedAddress.tsx +0 -29
  77. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/formatted/FormattedEmail.tsx +0 -17
  78. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/formatted/FormattedPhone.tsx +0 -24
  79. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/formatted/FormattedText.tsx +0 -11
  80. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/detail/formatted/FormattedUrl.tsx +0 -29
  81. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/filters/FilterField.tsx +0 -54
  82. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/filters/FilterInput.tsx +0 -55
  83. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/filters/FilterSelect.tsx +0 -72
  84. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/filters/FiltersPanel.tsx +0 -380
  85. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/forms/filters-form.tsx +0 -114
  86. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/forms/submit-button.tsx +0 -47
  87. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/search/GlobalSearchInput.tsx +0 -114
  88. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/search/ResultCardFields.tsx +0 -71
  89. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/search/SearchHeader.tsx +0 -31
  90. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/search/SearchResultCard.tsx +0 -138
  91. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/search/SearchResultsPanel.tsx +0 -197
  92. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/components/shared/LoadingFallback.tsx +0 -61
  93. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/constants.ts +0 -39
  94. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/filters/FilterInput.tsx +0 -55
  95. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/filters/FilterSelect.tsx +0 -72
  96. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/hooks/form.tsx +0 -209
  97. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/hooks/useObjectInfoBatch.ts +0 -72
  98. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/hooks/useObjectSearchData.ts +0 -174
  99. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/hooks/useRecordDetailLayout.ts +0 -137
  100. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/hooks/useRecordListGraphQL.ts +0 -135
  101. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/pages/DetailPage.tsx +0 -109
  102. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/pages/GlobalSearch.tsx +0 -235
  103. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/types/filters/filters.ts +0 -121
  104. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/types/filters/picklist.ts +0 -6
  105. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/types/objectInfo/objectInfo.ts +0 -49
  106. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/types/recordDetail/recordDetail.ts +0 -61
  107. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/types/schema.d.ts +0 -200
  108. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/apiUtils.ts +0 -59
  109. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/cacheUtils.ts +0 -76
  110. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/debounce.ts +0 -90
  111. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/fieldUtils.ts +0 -354
  112. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/fieldValueExtractor.ts +0 -67
  113. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/filterUtils.ts +0 -32
  114. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/formDataTransformUtils.ts +0 -260
  115. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/formUtils.ts +0 -142
  116. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/graphQLNodeFieldUtils.ts +0 -186
  117. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/graphQLObjectInfoAdapter.ts +0 -77
  118. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/graphQLRecordAdapter.ts +0 -90
  119. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/layoutTransformUtils.ts +0 -236
  120. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/linkUtils.ts +0 -14
  121. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/paginationUtils.ts +0 -49
  122. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/recordUtils.ts +0 -159
  123. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/features/global-search/utils/sanitizationUtils.ts +0 -50
  124. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/hooks/usePropertyListingPriceRange.ts +0 -64
  125. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/index.ts +0 -120
  126. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/About.tsx +0 -8
  127. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/HelpCenter.tsx +0 -29
  128. package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/PropertyListings.tsx +0 -100
  129. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/{applicationApi.ts → applications/applicationApi.ts} +0 -0
  130. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/{maintenanceRequestApi.ts → maintenanceRequests/maintenanceRequestApi.ts} +0 -0
  131. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/{propertyDetailGraphQL.ts → properties/propertyDetailGraphQL.ts} +0 -0
  132. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{WeatherWidget.tsx → dashboard/WeatherWidget.tsx} +0 -0
  133. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{NavMenu.tsx → layout/VerticalNav.tsx} +0 -0
  134. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{MaintenanceRequestIcon.tsx → maintenanceRequests/MaintenanceRequestIcon.tsx} +0 -0
  135. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{StatusBadge.tsx → maintenanceRequests/StatusBadge.tsx} +0 -0
  136. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{PropertyMap.tsx → properties/PropertyMap.tsx} +0 -0
  137. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/{PropertySearchFilters.tsx → properties/PropertySearchFilters.tsx} +0 -0
  138. /package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/{features/global-search/types/search → types}/searchResults.ts +0 -0
@@ -2,21 +2,24 @@
2
2
  * Thin GraphQL client: createDataSDK + data.graphql with centralized error handling.
3
3
  * Use with gql-tagged queries and generated operation types for type-safe calls.
4
4
  */
5
- import { createDataSDK } from "@salesforce/sdk-data";
5
+ import { createDataSDK } from '@salesforce/sdk-data';
6
6
 
7
- export async function executeGraphQL<TData, TVariables = Record<string, unknown>>(
8
- query: string | { kind: string; definitions: unknown[] },
9
- variables?: TVariables,
7
+ export async function executeGraphQL<TData, TVariables>(
8
+ query: string,
9
+ variables?: TVariables
10
10
  ): Promise<TData> {
11
- const data = await createDataSDK();
12
- // SDK types graphql() first param as string; at runtime it may accept gql DocumentNode too
13
- const response = await data.graphql?.<TData>(
14
- query as unknown as string,
15
- variables as Record<string, unknown>,
16
- );
17
- if (response?.errors?.length) {
18
- const msg = response.errors.map((e) => e.message).join("; ");
19
- throw new Error(`GraphQL Error: ${msg}`);
20
- }
21
- return (response?.data ?? {}) as TData;
11
+ const data = await createDataSDK();
12
+ // SDK types graphql() first param as string; at runtime it may accept gql DocumentNode too
13
+ const response = await data.graphql?.<TData, TVariables>(query, variables);
14
+
15
+ if (!response) {
16
+ throw new Error('GraphQL response is undefined');
17
+ }
18
+
19
+ if (response?.errors?.length) {
20
+ const msg = response.errors.map(e => e.message).join('; ');
21
+ throw new Error(`GraphQL Error: ${msg}`);
22
+ }
23
+
24
+ return response.data;
22
25
  }
@@ -13,7 +13,7 @@ import type {
13
13
  SearchResultRecord,
14
14
  SearchResultRecordData,
15
15
  FieldValue,
16
- } from "@/features/global-search/types/search/searchResults.js";
16
+ } from "@/types/searchResults.js";
17
17
 
18
18
  const OBJECT_API_NAME = "Property_Listing__c";
19
19
 
@@ -1,13 +1,15 @@
1
1
  import { useState } from "react";
2
2
  import { Outlet } from "react-router";
3
- import { TopBar } from "@/components/TopBar";
4
- import { NavMenu } from "@/components/NavMenu";
3
+ import { TopBar } from "@/components/layout/TopBar";
4
+ import { NavMenu } from "@/components/layout/VerticalNav";
5
+ import { Toaster } from "@/components/ui/sonner";
5
6
 
6
7
  export default function AppLayout() {
7
8
  const [isNavOpen, setIsNavOpen] = useState(false);
8
9
 
9
10
  return (
10
11
  <div className="flex flex-col">
12
+ <Toaster />
11
13
  <TopBar onMenuClick={() => setIsNavOpen(true)} />
12
14
 
13
15
  <div className="flex flex-1 overflow-hidden">
@@ -1,8 +1,8 @@
1
1
  import { useState } from "react";
2
2
  import { ChevronDown, Menu, UserPen, LogOut, User, Loader2 } from "lucide-react";
3
3
  import { Link } from "react-router";
4
- import { useAuth } from "../features/authentication/context/AuthContext";
5
- import { ROUTES } from "../features/authentication/authenticationConfig";
4
+ import { useAuth } from "@/features/authentication/context/AuthContext";
5
+ import { ROUTES } from "@/features/authentication/authenticationConfig";
6
6
  import zenLogo from "@/assets/icons/zen-logo.svg";
7
7
 
8
8
  export interface TopBarProps {
@@ -1,7 +1,7 @@
1
1
  import { useState } from "react";
2
- import type { MaintenanceRequestSummary } from "@/api/maintenanceRequestApi";
3
- import MaintenanceRequestListItem from "@/components/MaintenanceRequestListItem";
4
- import MaintenanceDetailsModal from "@/components/MaintenanceDetailsModal";
2
+ import type { MaintenanceRequestSummary } from "@/api/maintenanceRequests/maintenanceRequestApi";
3
+ import MaintenanceRequestListItem from "@/components/maintenanceRequests/MaintenanceRequestListItem";
4
+ import MaintenanceSummaryDetailsModal from "@/components/maintenanceRequests/MaintenanceSummaryDetailsModal";
5
5
  import { SkeletonListRows } from "@/components/SkeletonPrimitives";
6
6
 
7
7
  interface MaintenanceRequestListProps {
@@ -22,7 +22,7 @@ export default function MaintenanceRequestList({
22
22
  return (
23
23
  <>
24
24
  {selectedRequest && (
25
- <MaintenanceDetailsModal
25
+ <MaintenanceSummaryDetailsModal
26
26
  request={selectedRequest}
27
27
  onClose={() => setSelectedRequest(null)}
28
28
  />
@@ -2,9 +2,9 @@
2
2
  * Single maintenance request row: icon (teal) | Type & address + title | tenant (gray circle) [| status].
3
3
  */
4
4
  import { useCallback } from "react";
5
- import type { MaintenanceRequestSummary } from "@/api/maintenanceRequestApi";
6
- import { MaintenanceRequestIcon } from "@/components/MaintenanceRequestIcon";
7
- import { StatusBadge } from "@/components/StatusBadge";
5
+ import type { MaintenanceRequestSummary } from "@/api/maintenanceRequests/maintenanceRequestApi";
6
+ import { MaintenanceRequestIcon } from "@/components/maintenanceRequests/MaintenanceRequestIcon";
7
+ import { StatusBadge } from "@/components/maintenanceRequests/StatusBadge";
8
8
 
9
9
  export interface MaintenanceRequestListItemProps {
10
10
  request: MaintenanceRequestSummary;
@@ -0,0 +1,87 @@
1
+ /**
2
+ * Read-only maintenance details for B2C Maintenance page (summary rows from maintenanceRequestApi).
3
+ */
4
+ import { useEffect } from "react";
5
+ import { X } from "lucide-react";
6
+ import { StatusBadge } from "@/components/maintenanceRequests/StatusBadge";
7
+ import type { MaintenanceRequestSummary } from "@/api/maintenanceRequests/maintenanceRequestApi";
8
+
9
+ export interface MaintenanceSummaryDetailsModalProps {
10
+ request: MaintenanceRequestSummary;
11
+ onClose: () => void;
12
+ }
13
+
14
+ function formatDate(value: string | null): string {
15
+ if (!value?.trim()) return "—";
16
+ try {
17
+ const d = new Date(value);
18
+ return d.toLocaleDateString("en-US", {
19
+ month: "short",
20
+ day: "numeric",
21
+ year: "numeric",
22
+ hour: "numeric",
23
+ minute: "2-digit",
24
+ hour12: true,
25
+ });
26
+ } catch {
27
+ return value;
28
+ }
29
+ }
30
+
31
+ export default function MaintenanceSummaryDetailsModal({
32
+ request,
33
+ onClose,
34
+ }: MaintenanceSummaryDetailsModalProps) {
35
+ useEffect(() => {
36
+ const handleEscape = (e: KeyboardEvent) => {
37
+ if (e.key === "Escape") onClose();
38
+ };
39
+ document.addEventListener("keydown", handleEscape);
40
+ return () => document.removeEventListener("keydown", handleEscape);
41
+ }, [onClose]);
42
+
43
+ return (
44
+ <div className="fixed inset-0 z-50 flex items-center justify-center p-4">
45
+ <div className="fixed inset-0 bg-black/50" onClick={onClose} aria-hidden />
46
+ <div
47
+ role="dialog"
48
+ aria-modal
49
+ className="relative max-h-[90vh] w-full max-w-lg overflow-y-auto rounded-lg bg-white shadow-xl"
50
+ >
51
+ <div className="flex items-center justify-between border-b p-4">
52
+ <h2 className="text-lg font-semibold">{request.title ?? request.name ?? "Request"}</h2>
53
+ <button type="button" onClick={onClose} className="text-gray-500 hover:text-gray-800">
54
+ <X className="h-5 w-5" />
55
+ </button>
56
+ </div>
57
+ <div className="space-y-3 p-4 text-sm">
58
+ {request.description && <p className="text-gray-700">{request.description}</p>}
59
+ <div className="flex flex-wrap gap-2">
60
+ {request.type && (
61
+ <span className="rounded bg-gray-100 px-2 py-0.5">{request.type}</span>
62
+ )}
63
+ {request.priority && (
64
+ <span className="rounded bg-gray-100 px-2 py-0.5">{request.priority}</span>
65
+ )}
66
+ {request.status && <StatusBadge status={request.status} />}
67
+ </div>
68
+ {request.propertyAddress && (
69
+ <p>
70
+ <span className="font-medium">Property:</span> {request.propertyAddress}
71
+ </p>
72
+ )}
73
+ {request.tenantName && (
74
+ <p>
75
+ <span className="font-medium">Tenant:</span> {request.tenantName}
76
+ </p>
77
+ )}
78
+ {request.dateRequested && (
79
+ <p>
80
+ <span className="font-medium">Requested:</span> {formatDate(request.dateRequested)}
81
+ </p>
82
+ )}
83
+ </div>
84
+ </div>
85
+ </div>
86
+ );
87
+ }
@@ -6,7 +6,7 @@ import { useNavigate } from "react-router";
6
6
  import { useCallback, type MouseEvent } from "react";
7
7
  import { Button } from "@/components/ui/button";
8
8
  import { Skeleton } from "@/components/ui/skeleton";
9
- import type { SearchResultRecordData } from "@/features/global-search/types/search/searchResults.js";
9
+ import type { SearchResultRecordData } from "@/types/searchResults.js";
10
10
 
11
11
  function fieldDisplay(
12
12
  fields: Record<string, { value?: unknown; displayValue?: string | null }> | undefined,
@@ -1,39 +1,35 @@
1
1
  /**
2
- * SearchPagination Component
3
- *
4
- * Displays pagination controls for search results.
5
- * Previous/Next are disabled using hasPreviousPage/hasNextPage from the API so no request is made when there is no page.
6
- *
7
- * @remarks
8
- * - Layout: page size selector on the left, prev/page/next controls on the right (corners).
9
- * - Previous disabled when !hasPreviousPage (cursor stack enables prev when pageIndex > 0).
10
- * - Next disabled when !hasNextPage or nextPageToken is null.
2
+ * Pagination controls for Property_Listing__c consumer search (token-based).
3
+ * Replaces feature-react-global-search SearchPagination without pulling in that feature.
11
4
  */
12
- import { Button } from "../../../../components/ui/button";
5
+ import { Button } from "@/components/ui/button";
13
6
  import {
14
7
  Select,
15
8
  SelectContent,
16
9
  SelectItem,
17
10
  SelectTrigger,
18
11
  SelectValue,
19
- } from "../../../../components/ui/select";
20
- import { Label } from "../../../../components/ui/label";
21
- import { PAGE_SIZE_OPTIONS, getValidPageSize, isValidPageSize } from "../../utils/paginationUtils";
12
+ } from "@/components/ui/select";
13
+ import { Label } from "@/components/ui/label";
14
+ import {
15
+ PAGE_SIZE_OPTIONS,
16
+ getValidPageSize,
17
+ isValidPageSize,
18
+ } from "@/utils/propertyListingPaginationUtils";
22
19
  import { ChevronLeft, ChevronRight } from "lucide-react";
23
20
 
24
- interface SearchPaginationProps {
21
+ interface PropertyListingSearchPaginationProps {
25
22
  currentPageToken: string;
26
23
  nextPageToken: string | null;
27
24
  previousPageToken: string | null;
28
25
  hasNextPage?: boolean;
29
26
  hasPreviousPage?: boolean;
30
27
  pageSize: number;
31
- /** direction: 'prev' | 'next' | 'first'. When 'first' (e.g. page size change), parent typically resets pagination; token may be '' for prev when going to page 0. */
32
28
  onPageChange: (newPageToken: string, direction?: "next" | "prev" | "first") => void;
33
29
  onPageSizeChange: (newPageSize: number) => void;
34
30
  }
35
31
 
36
- export default function SearchPagination({
32
+ export default function PropertyListingSearchPagination({
37
33
  currentPageToken,
38
34
  nextPageToken,
39
35
  previousPageToken,
@@ -42,7 +38,7 @@ export default function SearchPagination({
42
38
  pageSize,
43
39
  onPageChange,
44
40
  onPageSizeChange,
45
- }: SearchPaginationProps) {
41
+ }: PropertyListingSearchPaginationProps) {
46
42
  const validPageSize = getValidPageSize(pageSize);
47
43
 
48
44
  const currentPageTokenNum = parseInt(currentPageToken, 10) || 0;
@@ -73,23 +69,19 @@ export default function SearchPagination({
73
69
 
74
70
  return (
75
71
  <nav
76
- className="w-full flex flex-row flex-wrap items-center justify-between gap-4 py-2"
72
+ className="flex w-full flex-row flex-wrap items-center justify-between gap-4 py-2"
77
73
  aria-label="Search results pagination"
78
74
  >
79
75
  <div
80
- className="flex items-center gap-2 shrink-0"
76
+ className="flex shrink-0 items-center gap-2"
81
77
  role="group"
82
78
  aria-label="Page size selector"
83
79
  >
84
- <Label htmlFor="page-size-select" className="text-sm font-normal whitespace-nowrap">
80
+ <Label htmlFor="page-size-select" className="whitespace-nowrap text-sm font-normal">
85
81
  Results per page:
86
82
  </Label>
87
83
  <Select value={validPageSize.toString()} onValueChange={handlePageSizeChange}>
88
- <SelectTrigger
89
- id="page-size-select"
90
- className="w-[70px]"
91
- aria-label="Select number of results per page"
92
- >
84
+ <SelectTrigger id="page-size-select" className="w-[70px]" aria-label="Results per page">
93
85
  <SelectValue />
94
86
  </SelectTrigger>
95
87
  <SelectContent>
@@ -102,7 +94,7 @@ export default function SearchPagination({
102
94
  </Select>
103
95
  </div>
104
96
 
105
- <div className="flex items-center gap-1 shrink-0" role="group" aria-label="Page navigation">
97
+ <div className="flex shrink-0 items-center gap-1" role="group" aria-label="Page navigation">
106
98
  <Button
107
99
  type="button"
108
100
  variant="outline"
@@ -119,9 +111,9 @@ export default function SearchPagination({
119
111
  Previous
120
112
  </Button>
121
113
  <span
122
- className="min-w-[4rem] text-center text-sm text-muted-foreground px-2"
123
- aria-label={`Page ${currentPage}, current page`}
114
+ className="min-w-[4rem] px-2 text-center text-sm text-muted-foreground"
124
115
  aria-current="page"
116
+ aria-label={`Page ${currentPage}, current page`}
125
117
  >
126
118
  Page {currentPage}
127
119
  </span>
@@ -0,0 +1,4 @@
1
+ /**
2
+ * Defaults for consumer property listing search (map + list), independent of object-search admin pages.
3
+ */
4
+ export const DEFAULT_PAGE_SIZE = 20;
@@ -0,0 +1,46 @@
1
+ import SEARCH_ACCOUNTS_QUERY from "./query/searchAccounts.graphql?raw";
2
+ import DISTINCT_INDUSTRIES_QUERY from "./query/distinctAccountIndustries.graphql?raw";
3
+ import DISTINCT_TYPES_QUERY from "./query/distinctAccountTypes.graphql?raw";
4
+ import {
5
+ searchObjects,
6
+ fetchDistinctValues,
7
+ type ObjectSearchOptions,
8
+ type PicklistOption,
9
+ } from "../../api/objectSearchService";
10
+ import type {
11
+ SearchAccountsQuery,
12
+ SearchAccountsQueryVariables,
13
+ DistinctAccountIndustriesQuery,
14
+ DistinctAccountTypesQuery,
15
+ } from "../../../../api/graphql-operations-types";
16
+
17
+ export type AccountSearchResult = NonNullable<SearchAccountsQuery["uiapi"]["query"]["Account"]>;
18
+
19
+ export type AccountSearchOptions = ObjectSearchOptions<
20
+ SearchAccountsQueryVariables["where"],
21
+ SearchAccountsQueryVariables["orderBy"]
22
+ >;
23
+
24
+ export type { PicklistOption };
25
+
26
+ export async function searchAccounts(
27
+ options: AccountSearchOptions = {},
28
+ ): Promise<AccountSearchResult> {
29
+ return searchObjects<AccountSearchResult, SearchAccountsQuery, SearchAccountsQueryVariables>(
30
+ SEARCH_ACCOUNTS_QUERY,
31
+ "Account",
32
+ options,
33
+ );
34
+ }
35
+
36
+ export async function fetchDistinctIndustries(): Promise<PicklistOption[]> {
37
+ return fetchDistinctValues<DistinctAccountIndustriesQuery>(
38
+ DISTINCT_INDUSTRIES_QUERY,
39
+ "Account",
40
+ "Industry",
41
+ );
42
+ }
43
+
44
+ export async function fetchDistinctTypes(): Promise<PicklistOption[]> {
45
+ return fetchDistinctValues<DistinctAccountTypesQuery>(DISTINCT_TYPES_QUERY, "Account", "Type");
46
+ }
@@ -0,0 +1,19 @@
1
+ query DistinctAccountIndustries {
2
+ uiapi {
3
+ aggregate {
4
+ Account(groupBy: { Industry: { group: true } }) {
5
+ edges {
6
+ node {
7
+ aggregate @optional {
8
+ Industry @optional {
9
+ value
10
+ displayValue
11
+ label
12
+ }
13
+ }
14
+ }
15
+ }
16
+ }
17
+ }
18
+ }
19
+ }
@@ -0,0 +1,19 @@
1
+ query DistinctAccountTypes {
2
+ uiapi {
3
+ aggregate {
4
+ Account(groupBy: { Type: { group: true } }) {
5
+ edges {
6
+ node {
7
+ aggregate @optional {
8
+ Type @optional {
9
+ value
10
+ displayValue
11
+ label
12
+ }
13
+ }
14
+ }
15
+ }
16
+ }
17
+ }
18
+ }
19
+ }
@@ -0,0 +1,121 @@
1
+ query GetAccountDetail($id: ID!) {
2
+ uiapi {
3
+ query {
4
+ Account(where: { Id: { eq: $id } }) {
5
+ edges {
6
+ node {
7
+ Id
8
+ Name @optional {
9
+ value
10
+ displayValue
11
+ }
12
+ Owner @optional {
13
+ Name @optional {
14
+ value
15
+ displayValue
16
+ }
17
+ }
18
+ Phone @optional {
19
+ value
20
+ displayValue
21
+ }
22
+ Fax @optional {
23
+ value
24
+ displayValue
25
+ }
26
+ Parent @optional {
27
+ Name @optional {
28
+ value
29
+ displayValue
30
+ }
31
+ }
32
+ Website @optional {
33
+ value
34
+ displayValue
35
+ }
36
+ Type @optional {
37
+ value
38
+ displayValue
39
+ }
40
+ NumberOfEmployees @optional {
41
+ value
42
+ displayValue
43
+ }
44
+ Industry @optional {
45
+ value
46
+ displayValue
47
+ }
48
+ AnnualRevenue @optional {
49
+ value
50
+ displayValue
51
+ }
52
+ Description @optional {
53
+ value
54
+ displayValue
55
+ }
56
+ BillingStreet @optional {
57
+ value
58
+ displayValue
59
+ }
60
+ BillingCity @optional {
61
+ value
62
+ displayValue
63
+ }
64
+ BillingState @optional {
65
+ value
66
+ displayValue
67
+ }
68
+ BillingPostalCode @optional {
69
+ value
70
+ displayValue
71
+ }
72
+ BillingCountry @optional {
73
+ value
74
+ displayValue
75
+ }
76
+ ShippingStreet @optional {
77
+ value
78
+ displayValue
79
+ }
80
+ ShippingCity @optional {
81
+ value
82
+ displayValue
83
+ }
84
+ ShippingState @optional {
85
+ value
86
+ displayValue
87
+ }
88
+ ShippingPostalCode @optional {
89
+ value
90
+ displayValue
91
+ }
92
+ ShippingCountry @optional {
93
+ value
94
+ displayValue
95
+ }
96
+ CreatedBy @optional {
97
+ Name @optional {
98
+ value
99
+ displayValue
100
+ }
101
+ }
102
+ CreatedDate @optional {
103
+ value
104
+ displayValue
105
+ }
106
+ LastModifiedBy @optional {
107
+ Name @optional {
108
+ value
109
+ displayValue
110
+ }
111
+ }
112
+ LastModifiedDate @optional {
113
+ value
114
+ displayValue
115
+ }
116
+ }
117
+ }
118
+ }
119
+ }
120
+ }
121
+ }
@@ -0,0 +1,51 @@
1
+ query SearchAccounts(
2
+ $first: Int
3
+ $after: String
4
+ $where: Account_Filter
5
+ $orderBy: Account_OrderBy
6
+ ) {
7
+ uiapi {
8
+ query {
9
+ Account(first: $first, after: $after, where: $where, orderBy: $orderBy) {
10
+ edges {
11
+ node {
12
+ Id
13
+ Name @optional {
14
+ value
15
+ displayValue
16
+ }
17
+ Industry @optional {
18
+ value
19
+ displayValue
20
+ }
21
+ Type @optional {
22
+ value
23
+ displayValue
24
+ }
25
+ Phone @optional {
26
+ value
27
+ displayValue
28
+ }
29
+ Owner @optional {
30
+ Name @optional {
31
+ value
32
+ displayValue
33
+ }
34
+ }
35
+ AnnualRevenue @optional {
36
+ value
37
+ displayValue
38
+ }
39
+ }
40
+ }
41
+ pageInfo {
42
+ hasNextPage
43
+ hasPreviousPage
44
+ endCursor
45
+ startCursor
46
+ }
47
+ totalCount
48
+ }
49
+ }
50
+ }
51
+ }