@salesforce/webapp-template-app-react-template-b2x-experimental 1.71.0 → 1.71.2
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.
- package/dist/CHANGELOG.md +16 -0
- package/dist/README.md +58 -4
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/package.json +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/components/alerts/status-alert.tsx +36 -32
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/components/layouts/card-layout.tsx +29 -0
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/footers/footer-link.tsx +1 -1
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/forms/auth-form.tsx +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/forms/submit-button.tsx +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/hooks/form.tsx +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/layout/card-skeleton.tsx +2 -2
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/layout/centered-page-layout.tsx +1 -1
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/layouts/AuthAppLayout.tsx +1 -1
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/pages/ResetPassword.tsx +2 -2
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/sessionTimeout/SessionTimeoutValidator.tsx +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{api → features/global-search/api}/objectDetailService.ts +2 -2
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/DetailHeader.tsx +1 -1
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/filters/FilterInput.tsx +2 -2
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/filters/FilterSelect.tsx +2 -2
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components/filters}/FiltersPanel.tsx +15 -10
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/forms/filters-form.tsx +4 -4
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/forms/submit-button.tsx +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components/shared → features/global-search/components/search}/GlobalSearchInput.tsx +4 -4
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/search/SearchPagination.tsx +3 -3
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components/search}/SearchResultCard.tsx +10 -5
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/search/SearchResultsPanel.tsx +5 -5
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components/shared}/LoadingFallback.tsx +1 -1
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/features/global-search/filters/FilterInput.tsx +55 -0
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/features/global-search/filters/FilterSelect.tsx +72 -0
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{hooks → features/global-search/hooks}/form.tsx +9 -4
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{pages → features/global-search/pages}/DetailPage.tsx +4 -4
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{pages → features/global-search/pages}/GlobalSearch.tsx +4 -4
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/pages/Home.tsx +1 -1
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/routes.tsx +13 -13
- package/dist/package.json +1 -1
- package/package.json +1 -1
- package/dist/force-app/main/default/README.md +0 -72
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/auth/alerts/status-alert.tsx +0 -45
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/auth/layout/card-layout.tsx +0 -29
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/components/layout/card-layout.tsx +0 -19
- package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/features/global-search/index.ts +0 -33
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/authHelpers.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/authenticationConfig.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/context/AuthContext.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/hooks/useCountdownTimer.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/hooks/useRetryWithBackoff.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/layouts/authenticationRouteLayout.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/layouts/privateRouteLayout.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/pages/ChangePassword.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/pages/ForgotPassword.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/pages/Login.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/pages/Profile.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/pages/Register.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/sessionTimeout/sessionTimeService.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/sessionTimeout/sessionTimeoutConfig.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{auth → features/authentication}/utils/helpers.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{api → features/global-search/api}/index.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{api → features/global-search/api}/objectInfoGraphQLService.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{api → features/global-search/api}/objectInfoService.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{api → features/global-search/api}/recordListGraphQLService.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/DetailFields.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/DetailForm.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/DetailLayoutSections.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/Section.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/SectionRow.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/UiApiDetailForm.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/FieldValueDisplay.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/FormattedAddress.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/FormattedEmail.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/FormattedPhone.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/FormattedText.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/FormattedUrl.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/detail/formatted/index.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/filters/FilterField.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/search/ResultCardFields.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{components → features/global-search/components}/search/SearchHeader.tsx +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{hooks → features/global-search/hooks}/index.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{hooks → features/global-search/hooks}/useObjectInfoBatch.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{hooks → features/global-search/hooks}/useObjectSearchData.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{hooks → features/global-search/hooks}/useRecordDetailLayout.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{hooks → features/global-search/hooks}/useRecordListGraphQL.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{types → features/global-search/types}/filters/filters.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{types → features/global-search/types}/filters/picklist.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{types → features/global-search/types}/index.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{types → features/global-search/types}/objectInfo/objectInfo.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{types → features/global-search/types}/recordDetail/recordDetail.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{types → features/global-search/types}/search/searchResults.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/apiUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/cacheUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/debounce.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/fieldUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/fieldValueExtractor.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/filterUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/formDataTransformUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/formUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/graphQLNodeFieldUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/graphQLObjectInfoAdapter.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/graphQLRecordAdapter.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/index.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/layoutTransformUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/linkUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/paginationUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/recordUtils.ts +0 -0
- /package/dist/force-app/main/default/webapplications/appreacttemplateb2x/src/{utils → features/global-search/utils}/sanitizationUtils.ts +0 -0
package/dist/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,22 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
## [1.71.2](https://github.com/salesforce-experience-platform-emu/webapps/compare/v1.71.1...v1.71.2) (2026-03-05)
|
|
7
|
+
|
|
8
|
+
**Note:** Version bump only for package @salesforce/webapp-template-base-sfdx-project-experimental
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
## [1.71.1](https://github.com/salesforce-experience-platform-emu/webapps/compare/v1.71.0...v1.71.1) (2026-03-05)
|
|
15
|
+
|
|
16
|
+
**Note:** Version bump only for package @salesforce/webapp-template-base-sfdx-project-experimental
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
|
|
6
22
|
# [1.71.0](https://github.com/salesforce-experience-platform-emu/webapps/compare/v1.70.0...v1.71.0) (2026-03-05)
|
|
7
23
|
|
|
8
24
|
**Note:** Version bump only for package @salesforce/webapp-template-base-sfdx-project-experimental
|
package/dist/README.md
CHANGED
|
@@ -1,10 +1,64 @@
|
|
|
1
|
-
#
|
|
1
|
+
# App React Template B2X
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
A B2X (Business-to-Consumer) React starter template for customer-facing apps on the Salesforce platform. Includes authentication, global search, and an Experience Cloud site container. Built with React, Vite, TypeScript, and Tailwind/shadcn.
|
|
4
4
|
|
|
5
|
-
##
|
|
5
|
+
## What's included
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
| Path | Description |
|
|
8
|
+
| ------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------- |
|
|
9
|
+
| `force-app/main/default/webapplications/appreacttemplateb2x/` | React web app (source, config, tests) |
|
|
10
|
+
| `force-app/main/default/classes/` | Apex classes for authentication — `WebAppAuthUtils`, `WebAppChangePassword`, `WebAppForgotPassword`, `WebAppLogin`, `WebAppRegistration` |
|
|
11
|
+
| `force-app/main/default/digitalExperienceConfigs/` | Experience Cloud site configuration |
|
|
12
|
+
| `force-app/main/default/digitalExperiences/` | Experience Cloud site definition |
|
|
13
|
+
| `force-app/main/default/networks/` | Experience Cloud network |
|
|
14
|
+
| `force-app/main/default/sites/` | Salesforce site |
|
|
15
|
+
|
|
16
|
+
## Getting started
|
|
17
|
+
|
|
18
|
+
Navigate to the web app and install dependencies:
|
|
19
|
+
|
|
20
|
+
```bash
|
|
21
|
+
cd force-app/main/default/webapplications/appreacttemplateb2x
|
|
22
|
+
npm install
|
|
23
|
+
npm run dev
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
Opens at http://localhost:5173 by default. For build and test instructions, see the [web app README](force-app/main/default/webapplications/appreacttemplateb2x/README.md).
|
|
27
|
+
|
|
28
|
+
## Deploy
|
|
29
|
+
|
|
30
|
+
### Deploy everything (metadata + Experience Cloud site + web app)
|
|
31
|
+
|
|
32
|
+
```bash
|
|
33
|
+
cd force-app/main/default/webapplications/appreacttemplateb2x && npm install && npm run build && cd -
|
|
34
|
+
sf project deploy start --source-dir force-app --target-org <alias>
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
### Deploy the web app only
|
|
38
|
+
|
|
39
|
+
```bash
|
|
40
|
+
cd force-app/main/default/webapplications/appreacttemplateb2x && npm install && npm run build && cd -
|
|
41
|
+
sf project deploy start --source-dir force-app/main/default/webapplications --target-org <alias>
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
### Deploy Experience Cloud site only
|
|
45
|
+
|
|
46
|
+
```bash
|
|
47
|
+
sf project deploy start \
|
|
48
|
+
--source-dir force-app/main/default/digitalExperienceConfigs \
|
|
49
|
+
--source-dir force-app/main/default/digitalExperiences \
|
|
50
|
+
--source-dir force-app/main/default/networks \
|
|
51
|
+
--source-dir force-app/main/default/sites \
|
|
52
|
+
--target-org <alias>
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
### Deploy authentication classes only
|
|
56
|
+
|
|
57
|
+
```bash
|
|
58
|
+
sf project deploy start --source-dir force-app/main/default/classes --target-org <alias>
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
Replace `<alias>` with your target org alias.
|
|
8
62
|
|
|
9
63
|
## Configure Your Salesforce DX Project
|
|
10
64
|
|
|
@@ -15,8 +15,8 @@
|
|
|
15
15
|
"graphql:schema": "node scripts/get-graphql-schema.mjs"
|
|
16
16
|
},
|
|
17
17
|
"dependencies": {
|
|
18
|
-
"@salesforce/sdk-data": "^1.71.
|
|
19
|
-
"@salesforce/webapp-experimental": "^1.71.
|
|
18
|
+
"@salesforce/sdk-data": "^1.71.2",
|
|
19
|
+
"@salesforce/webapp-experimental": "^1.71.2",
|
|
20
20
|
"@tailwindcss/vite": "^4.1.17",
|
|
21
21
|
"@tanstack/react-form": "^1.28.4",
|
|
22
22
|
"class-variance-authority": "^0.7.1",
|
|
@@ -40,7 +40,7 @@
|
|
|
40
40
|
"@graphql-eslint/eslint-plugin": "^4.1.0",
|
|
41
41
|
"@graphql-tools/utils": "^11.0.0",
|
|
42
42
|
"@playwright/test": "^1.49.0",
|
|
43
|
-
"@salesforce/vite-plugin-webapp-experimental": "^1.71.
|
|
43
|
+
"@salesforce/vite-plugin-webapp-experimental": "^1.71.2",
|
|
44
44
|
"@testing-library/jest-dom": "^6.6.3",
|
|
45
45
|
"@testing-library/react": "^16.1.0",
|
|
46
46
|
"@testing-library/user-event": "^14.5.2",
|
|
@@ -1,45 +1,49 @@
|
|
|
1
|
-
import { cva, type VariantProps } from
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
1
|
+
import { cva, type VariantProps } from 'class-variance-authority';
|
|
2
|
+
import { AlertCircleIcon, CheckCircle2Icon } from 'lucide-react';
|
|
3
|
+
import { Alert, AlertDescription } from '../../components/ui/alert';
|
|
4
|
+
import { useId } from 'react';
|
|
5
5
|
|
|
6
|
-
const statusAlertVariants = cva(
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
6
|
+
const statusAlertVariants = cva('', {
|
|
7
|
+
variants: {
|
|
8
|
+
variant: {
|
|
9
|
+
error: '',
|
|
10
|
+
success: '',
|
|
11
|
+
},
|
|
12
|
+
},
|
|
13
|
+
defaultVariants: {
|
|
14
|
+
variant: 'error',
|
|
15
|
+
},
|
|
16
16
|
});
|
|
17
17
|
|
|
18
18
|
interface StatusAlertProps extends VariantProps<typeof statusAlertVariants> {
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
19
|
+
children?: React.ReactNode;
|
|
20
|
+
/** Alert variant type. @default "error" */
|
|
21
|
+
variant?: 'error' | 'success';
|
|
22
22
|
}
|
|
23
23
|
|
|
24
24
|
/**
|
|
25
25
|
* Status alert component for displaying error or success messages.
|
|
26
26
|
* Returns null if no children are provided.
|
|
27
27
|
*/
|
|
28
|
-
export function StatusAlert({ children, variant =
|
|
29
|
-
|
|
28
|
+
export function StatusAlert({ children, variant = 'error' }: StatusAlertProps) {
|
|
29
|
+
if (!children) return null;
|
|
30
30
|
|
|
31
|
-
|
|
32
|
-
|
|
31
|
+
const isError = variant === 'error';
|
|
32
|
+
const descriptionId = useId();
|
|
33
33
|
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
34
|
+
return (
|
|
35
|
+
<Alert
|
|
36
|
+
variant={isError ? 'destructive' : 'default'}
|
|
37
|
+
className={statusAlertVariants({ variant })}
|
|
38
|
+
aria-describedby={descriptionId}
|
|
39
|
+
role={isError ? 'alert' : 'status'}
|
|
40
|
+
>
|
|
41
|
+
{isError ? (
|
|
42
|
+
<AlertCircleIcon aria-hidden="true" />
|
|
43
|
+
) : (
|
|
44
|
+
<CheckCircle2Icon aria-hidden="true" />
|
|
45
|
+
)}
|
|
46
|
+
<AlertDescription id={descriptionId}>{children}</AlertDescription>
|
|
47
|
+
</Alert>
|
|
48
|
+
);
|
|
45
49
|
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Card,
|
|
3
|
+
CardContent,
|
|
4
|
+
CardDescription,
|
|
5
|
+
CardHeader,
|
|
6
|
+
CardTitle,
|
|
7
|
+
} from '../../components/ui/card';
|
|
8
|
+
|
|
9
|
+
interface CardLayoutProps {
|
|
10
|
+
title: string;
|
|
11
|
+
description?: string;
|
|
12
|
+
children: React.ReactNode;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Card layout component for authentication pages.
|
|
17
|
+
* Provides CardHeader with title and optional description, and CardContent.
|
|
18
|
+
*/
|
|
19
|
+
export function CardLayout({ title, description, children }: CardLayoutProps) {
|
|
20
|
+
return (
|
|
21
|
+
<Card>
|
|
22
|
+
<CardHeader>
|
|
23
|
+
<CardTitle className="text-2xl">{title}</CardTitle>
|
|
24
|
+
{description && <CardDescription>{description}</CardDescription>}
|
|
25
|
+
</CardHeader>
|
|
26
|
+
<CardContent>{children}</CardContent>
|
|
27
|
+
</Card>
|
|
28
|
+
);
|
|
29
|
+
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Link } from "react-router";
|
|
2
|
-
import { cn } from "
|
|
2
|
+
import { cn } from "../../../lib/utils";
|
|
3
3
|
|
|
4
4
|
interface FooterLinkProps extends Omit<React.ComponentProps<typeof Link>, "children"> {
|
|
5
5
|
/** Link text prefix (e.g., "Don't have an account?") */
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { FieldGroup } from "
|
|
2
|
-
import { StatusAlert } from "
|
|
1
|
+
import { FieldGroup } from "../../../components/ui/field";
|
|
2
|
+
import { StatusAlert } from "../../../components/alerts/status-alert";
|
|
3
3
|
import { FooterLink } from "../footers/footer-link";
|
|
4
4
|
import { SubmitButton } from "./submit-button";
|
|
5
|
-
import { CardLayout } from "
|
|
5
|
+
import { CardLayout } from "../../../components/layouts/card-layout";
|
|
6
6
|
import { useFormContext } from "../hooks/form";
|
|
7
7
|
import { useId } from "react";
|
|
8
8
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { Button } from "
|
|
2
|
-
import { Spinner } from "
|
|
3
|
-
import { cn } from "
|
|
1
|
+
import { Button } from "../../../components/ui/button";
|
|
2
|
+
import { Spinner } from "../../../components/ui/spinner";
|
|
3
|
+
import { cn } from "../../../lib/utils";
|
|
4
4
|
import { useFormContext } from "../hooks/form";
|
|
5
5
|
|
|
6
6
|
interface SubmitButtonProps extends Omit<React.ComponentProps<typeof Button>, "type"> {
|
|
@@ -5,9 +5,9 @@ import {
|
|
|
5
5
|
FieldDescription,
|
|
6
6
|
FieldError,
|
|
7
7
|
FieldLabel,
|
|
8
|
-
} from "
|
|
9
|
-
import { Input } from "
|
|
10
|
-
import { cn } from "
|
|
8
|
+
} from "../../../components/ui/field";
|
|
9
|
+
import { Input } from "../../../components/ui/input";
|
|
10
|
+
import { cn } from "../../../lib/utils";
|
|
11
11
|
import { AUTH_PLACEHOLDERS } from "../authenticationConfig";
|
|
12
12
|
|
|
13
13
|
// Create form hook contexts
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { CenteredPageLayout } from "./centered-page-layout";
|
|
2
|
-
import { Card, CardContent, CardHeader } from "
|
|
3
|
-
import { Skeleton } from "
|
|
2
|
+
import { Card, CardContent, CardHeader } from "../../../components/ui/card";
|
|
3
|
+
import { Skeleton } from "../../../components/ui/skeleton";
|
|
4
4
|
|
|
5
5
|
interface CardSkeletonProps {
|
|
6
6
|
/**
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import SessionTimeoutValidator from "../sessionTimeout/SessionTimeoutValidator";
|
|
2
2
|
import { AuthProvider } from "../context/AuthContext";
|
|
3
|
-
import AppLayout from "
|
|
3
|
+
import AppLayout from "../../../appLayout";
|
|
4
4
|
|
|
5
5
|
export default function AuthAppLayout() {
|
|
6
6
|
return (
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { useState } from "react";
|
|
2
2
|
import { Link, useSearchParams } from "react-router";
|
|
3
|
-
import { CardLayout } from "
|
|
3
|
+
import { CardLayout } from "../../../components/layouts/card-layout";
|
|
4
4
|
import { CenteredPageLayout } from "../layout/centered-page-layout";
|
|
5
5
|
import { AuthForm } from "../forms/auth-form";
|
|
6
|
-
import { StatusAlert } from "
|
|
6
|
+
import { StatusAlert } from "../../../components/alerts/status-alert";
|
|
7
7
|
import { useAppForm } from "../hooks/form";
|
|
8
8
|
import { getDataSDK } from "@salesforce/sdk-data";
|
|
9
9
|
import { ROUTES, AUTH_PLACEHOLDERS } from "../authenticationConfig";
|
|
@@ -10,8 +10,8 @@ import { useAuth } from "../context/AuthContext";
|
|
|
10
10
|
import { pollSessionTimeServlet, extendSessionTime } from "./sessionTimeService";
|
|
11
11
|
import { useCountdownTimer } from "../hooks/useCountdownTimer";
|
|
12
12
|
import { useRetryWithBackoff } from "../hooks/useRetryWithBackoff";
|
|
13
|
-
import { Alert, AlertTitle, AlertDescription } from "
|
|
14
|
-
import { Button } from "
|
|
13
|
+
import { Alert, AlertTitle, AlertDescription } from "../../../components/ui/alert";
|
|
14
|
+
import { Button } from "../../../components/ui/button";
|
|
15
15
|
import {
|
|
16
16
|
Dialog,
|
|
17
17
|
DialogContent,
|
|
@@ -19,7 +19,7 @@ import {
|
|
|
19
19
|
DialogTitle,
|
|
20
20
|
DialogDescription,
|
|
21
21
|
DialogFooter,
|
|
22
|
-
} from "
|
|
22
|
+
} from "../../../components/ui/dialog";
|
|
23
23
|
import {
|
|
24
24
|
STORAGE_KEYS,
|
|
25
25
|
LABELS,
|
|
@@ -11,9 +11,9 @@ import { uiApiClient } from "@salesforce/webapp-experimental/api";
|
|
|
11
11
|
import type { LayoutResponse } from "../types/recordDetail/recordDetail";
|
|
12
12
|
import { LayoutResponseSchema } from "../types/recordDetail/recordDetail";
|
|
13
13
|
import { fetchAndValidate, safeEncodePath } from "../utils/apiUtils";
|
|
14
|
-
import { objectInfoService } from "
|
|
14
|
+
import { objectInfoService } from "./objectInfoService";
|
|
15
15
|
import type { ObjectInfoResult } from "../types/objectInfo/objectInfo";
|
|
16
|
-
import { getRecordByIdGraphQL, type GraphQLRecordNode } from "
|
|
16
|
+
import { getRecordByIdGraphQL, type GraphQLRecordNode } from "./recordListGraphQLService";
|
|
17
17
|
import type { Column } from "../types/search/searchResults";
|
|
18
18
|
import { calculateFieldsToFetch } from "../utils/recordUtils";
|
|
19
19
|
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* @param title - Record title (e.g. record name) shown next to the back control.
|
|
5
5
|
* @param onBack - Called when the user activates the back control.
|
|
6
6
|
*/
|
|
7
|
-
import { Button } from "
|
|
7
|
+
import { Button } from "../../../../components/ui/button";
|
|
8
8
|
import { ArrowLeft } from "lucide-react";
|
|
9
9
|
|
|
10
10
|
interface DetailHeaderProps {
|
|
@@ -22,8 +22,8 @@
|
|
|
22
22
|
* />
|
|
23
23
|
* ```
|
|
24
24
|
*/
|
|
25
|
-
import { Input } from "
|
|
26
|
-
import { Field, FieldLabel, FieldDescription } from "
|
|
25
|
+
import { Input } from "../../../../components/ui/input";
|
|
26
|
+
import { Field, FieldLabel, FieldDescription } from "../../../../components/ui/field";
|
|
27
27
|
import type { Filter } from "../../types/filters/filters";
|
|
28
28
|
|
|
29
29
|
interface FilterInputProps {
|
|
@@ -30,8 +30,8 @@ import {
|
|
|
30
30
|
SelectItem,
|
|
31
31
|
SelectTrigger,
|
|
32
32
|
SelectValue,
|
|
33
|
-
} from "
|
|
34
|
-
import { Field, FieldLabel, FieldDescription } from "
|
|
33
|
+
} from "../../../../components/ui/select";
|
|
34
|
+
import { Field, FieldLabel, FieldDescription } from "../../../../components/ui/field";
|
|
35
35
|
import type { Filter } from "../../types/filters/filters";
|
|
36
36
|
import type { PicklistValue } from "../../types/filters/picklist";
|
|
37
37
|
|
|
@@ -27,16 +27,21 @@
|
|
|
27
27
|
* ```
|
|
28
28
|
*/
|
|
29
29
|
import { useState, useMemo, useCallback, useEffect, useRef } from "react";
|
|
30
|
-
import {
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
import
|
|
37
|
-
import {
|
|
38
|
-
import {
|
|
39
|
-
import {
|
|
30
|
+
import {
|
|
31
|
+
Card,
|
|
32
|
+
CardContent,
|
|
33
|
+
CardHeader,
|
|
34
|
+
CardTitle,
|
|
35
|
+
} from "../../../../components/ui/card";
|
|
36
|
+
import { Skeleton } from "../../../../components/ui/skeleton";
|
|
37
|
+
import { FiltersForm } from "../forms/filters-form";
|
|
38
|
+
import { Field, FieldLabel, FieldDescription } from "../../../../components/ui/field";
|
|
39
|
+
import { useAppForm, validateRangeValues } from "../../hooks/form";
|
|
40
|
+
import type { Filter, FilterCriteria } from "../../types/filters/filters";
|
|
41
|
+
import type { PicklistValue } from "../../types/filters/picklist";
|
|
42
|
+
import { parseFilterValue } from "../../utils/filterUtils";
|
|
43
|
+
import { sanitizeFilterValue } from "../../utils/sanitizationUtils";
|
|
44
|
+
import { getFormValueByPath } from "../../utils/formUtils";
|
|
40
45
|
|
|
41
46
|
interface FiltersPanelProps {
|
|
42
47
|
filters: Filter[];
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { FieldGroup } from "
|
|
2
|
-
import { StatusAlert } from "
|
|
3
|
-
import { CardLayout } from "
|
|
1
|
+
import { FieldGroup } from "../../../../components/ui/field";
|
|
2
|
+
import { StatusAlert } from "../../../../components/alerts/status-alert";
|
|
3
|
+
import { CardLayout } from "../../../../components/layouts/card-layout";
|
|
4
4
|
import { SubmitButton } from "./submit-button";
|
|
5
|
-
import { Button } from "
|
|
5
|
+
import { Button } from "../../../../components/ui/button";
|
|
6
6
|
import { useFormContext } from "../../hooks/form";
|
|
7
7
|
import { useId, useEffect, useRef } from "react";
|
|
8
8
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { Button } from "
|
|
2
|
-
import { Spinner } from "
|
|
3
|
-
import { cn } from "
|
|
1
|
+
import { Button } from "../../../../components/ui/button";
|
|
2
|
+
import { Spinner } from "../../../../components/ui/spinner";
|
|
3
|
+
import { cn } from "../../../../lib/utils";
|
|
4
4
|
import { useFormContext } from "../../hooks/form";
|
|
5
5
|
|
|
6
6
|
interface SubmitButtonProps extends Omit<React.ComponentProps<typeof Button>, "type" | "disabled"> {
|
|
@@ -7,11 +7,11 @@
|
|
|
7
7
|
import { useState, useCallback, useMemo, useId } from "react";
|
|
8
8
|
import type { KeyboardEvent, ChangeEvent } from "react";
|
|
9
9
|
import { useNavigate } from "react-router";
|
|
10
|
-
import { Card, CardContent } from "
|
|
11
|
-
import { Input } from "
|
|
12
|
-
import { Button } from "
|
|
10
|
+
import { Card, CardContent } from "../../../../components/ui/card";
|
|
11
|
+
import { Input } from "../../../../components/ui/input";
|
|
12
|
+
import { Button } from "../../../../components/ui/button";
|
|
13
13
|
import { Search } from "lucide-react";
|
|
14
|
-
import { OBJECT_API_NAMES } from "
|
|
14
|
+
import { OBJECT_API_NAMES } from "../../../../constants";
|
|
15
15
|
import { useObjectInfoBatch } from "../../hooks/useObjectInfoBatch";
|
|
16
16
|
|
|
17
17
|
const BROWSE_SEGMENT = "browse__all";
|
|
@@ -9,15 +9,15 @@
|
|
|
9
9
|
* - Previous disabled when !hasPreviousPage (cursor stack enables prev when pageIndex > 0).
|
|
10
10
|
* - Next disabled when !hasNextPage or nextPageToken is null.
|
|
11
11
|
*/
|
|
12
|
-
import { Button } from "
|
|
12
|
+
import { Button } from "../../../../components/ui/button";
|
|
13
13
|
import {
|
|
14
14
|
Select,
|
|
15
15
|
SelectContent,
|
|
16
16
|
SelectItem,
|
|
17
17
|
SelectTrigger,
|
|
18
18
|
SelectValue,
|
|
19
|
-
} from "
|
|
20
|
-
import { Label } from "
|
|
19
|
+
} from "../../../../components/ui/select";
|
|
20
|
+
import { Label } from "../../../../components/ui/label";
|
|
21
21
|
import { PAGE_SIZE_OPTIONS, getValidPageSize, isValidPageSize } from "../../utils/paginationUtils";
|
|
22
22
|
import { ChevronLeft, ChevronRight } from "lucide-react";
|
|
23
23
|
|
|
@@ -25,11 +25,16 @@
|
|
|
25
25
|
*/
|
|
26
26
|
import { useNavigate } from "react-router";
|
|
27
27
|
import { useMemo, useCallback } from "react";
|
|
28
|
-
import {
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
28
|
+
import {
|
|
29
|
+
Card,
|
|
30
|
+
CardContent,
|
|
31
|
+
CardHeader,
|
|
32
|
+
CardTitle,
|
|
33
|
+
} from "../../../../components/ui/card";
|
|
34
|
+
import type { Column, SearchResultRecordData } from "../../types/search/searchResults";
|
|
35
|
+
import { getNestedFieldValue } from "../../utils/fieldUtils";
|
|
36
|
+
import ResultCardFields from "./ResultCardFields";
|
|
37
|
+
import { OBJECT_API_NAMES } from "../../../../constants";
|
|
33
38
|
|
|
34
39
|
interface SearchResultCardProps {
|
|
35
40
|
record: SearchResultRecordData;
|
|
@@ -32,8 +32,8 @@
|
|
|
32
32
|
* ```
|
|
33
33
|
*/
|
|
34
34
|
import { useMemo } from "react";
|
|
35
|
-
import { Alert, AlertDescription, AlertTitle } from "
|
|
36
|
-
import { Skeleton } from "
|
|
35
|
+
import { Alert, AlertDescription, AlertTitle } from "../../../../components/ui/alert";
|
|
36
|
+
import { Skeleton } from "../../../../components/ui/skeleton";
|
|
37
37
|
import { AlertCircle } from "lucide-react";
|
|
38
38
|
import {
|
|
39
39
|
Select,
|
|
@@ -41,9 +41,9 @@ import {
|
|
|
41
41
|
SelectItem,
|
|
42
42
|
SelectTrigger,
|
|
43
43
|
SelectValue,
|
|
44
|
-
} from "
|
|
45
|
-
import { Label } from "
|
|
46
|
-
import SearchResultCard from "
|
|
44
|
+
} from "../../../../components/ui/select";
|
|
45
|
+
import { Label } from "../../../../components/ui/label";
|
|
46
|
+
import SearchResultCard from "./SearchResultCard";
|
|
47
47
|
import SearchPagination from "./SearchPagination";
|
|
48
48
|
import type { Column, SearchResultRecord } from "../../types/search/searchResults";
|
|
49
49
|
import { getSafeKey } from "../../utils/recordUtils";
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* FilterInput Component
|
|
3
|
+
*
|
|
4
|
+
* Renders a text input field for filter values.
|
|
5
|
+
* Used for filters that don't have a picklist (affordance !== 'select').
|
|
6
|
+
*
|
|
7
|
+
* @param filter - Filter definition containing field path, label, and attributes
|
|
8
|
+
* @param value - Current filter input value
|
|
9
|
+
* @param onChange - Callback when input value changes
|
|
10
|
+
*
|
|
11
|
+
* @remarks
|
|
12
|
+
* - Displays filter label or field path as the label
|
|
13
|
+
* - Shows placeholder text from filter attributes or generates default
|
|
14
|
+
* - Displays help message if available
|
|
15
|
+
*
|
|
16
|
+
* @example
|
|
17
|
+
* ```tsx
|
|
18
|
+
* <FilterInput
|
|
19
|
+
* filter={textFilter}
|
|
20
|
+
* value={filterValue}
|
|
21
|
+
* onChange={(value) => setFilterValue(value)}
|
|
22
|
+
* />
|
|
23
|
+
* ```
|
|
24
|
+
*/
|
|
25
|
+
import { Input } from "../../../components/ui/input";
|
|
26
|
+
import { Field, FieldLabel, FieldDescription } from "../../../components/ui/field";
|
|
27
|
+
import type { Filter } from "../types/filters/filters";
|
|
28
|
+
|
|
29
|
+
interface FilterInputProps {
|
|
30
|
+
filter: Filter;
|
|
31
|
+
value: string;
|
|
32
|
+
onChange: (value: string) => void;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
export default function FilterInput({ filter, value, onChange }: FilterInputProps) {
|
|
36
|
+
return (
|
|
37
|
+
<Field>
|
|
38
|
+
<FieldLabel htmlFor={filter.targetFieldPath}>
|
|
39
|
+
{filter.label || filter.targetFieldPath}
|
|
40
|
+
</FieldLabel>
|
|
41
|
+
<Input
|
|
42
|
+
id={filter.targetFieldPath}
|
|
43
|
+
type="text"
|
|
44
|
+
value={value}
|
|
45
|
+
onChange={(e: React.ChangeEvent<HTMLInputElement>) => onChange(e.target.value)}
|
|
46
|
+
placeholder={
|
|
47
|
+
filter.attributes?.placeholder ||
|
|
48
|
+
`Enter ${(filter.label || filter.targetFieldPath).toLowerCase()}`
|
|
49
|
+
}
|
|
50
|
+
aria-label={filter.label || filter.targetFieldPath}
|
|
51
|
+
/>
|
|
52
|
+
{filter.helpMessage && <FieldDescription>{filter.helpMessage}</FieldDescription>}
|
|
53
|
+
</Field>
|
|
54
|
+
);
|
|
55
|
+
}
|