@salesforce/webapp-template-app-react-sample-b2x-experimental 1.36.3
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/LICENSE.txt +82 -0
- package/dist/.a4drules/build-validation.md +81 -0
- package/dist/.a4drules/code-quality.md +150 -0
- package/dist/.a4drules/graphql/tools/knowledge/lds-explore-graphql-schema.md +227 -0
- package/dist/.a4drules/graphql/tools/knowledge/lds-generate-graphql-mutationquery.md +212 -0
- package/dist/.a4drules/graphql/tools/knowledge/lds-generate-graphql-readquery.md +185 -0
- package/dist/.a4drules/graphql/tools/knowledge/lds-guide-graphql.md +205 -0
- package/dist/.a4drules/graphql/tools/schemas/shared.graphqls +1150 -0
- package/dist/.a4drules/graphql.md +408 -0
- package/dist/.a4drules/images.md +13 -0
- package/dist/.a4drules/react.md +361 -0
- package/dist/.a4drules/react_image_processing.md +45 -0
- package/dist/.a4drules/skills/install-feature/SKILL.md +67 -0
- package/dist/.a4drules/skills/install-feature/scripts/copy-feature-assets.sh +36 -0
- package/dist/.a4drules/typescript.md +224 -0
- package/dist/.forceignore +15 -0
- package/dist/.husky/pre-commit +4 -0
- package/dist/.prettierignore +11 -0
- package/dist/.prettierrc +17 -0
- package/dist/CHANGELOG.md +533 -0
- package/dist/README.md +18 -0
- package/dist/config/project-scratch-def.json +13 -0
- package/dist/force-app/main/default/digitalExperienceConfigs/appreactsampleb2x1.digitalExperienceConfig +8 -0
- package/dist/force-app/main/default/digitalExperiences/site/appreactsampleb2x1/appreactsampleb2x1.digitalExperience-meta.xml +11 -0
- package/dist/force-app/main/default/digitalExperiences/site/appreactsampleb2x1/sfdc_cms__site/appreactsampleb2x1/_meta.json +5 -0
- package/dist/force-app/main/default/digitalExperiences/site/appreactsampleb2x1/sfdc_cms__site/appreactsampleb2x1/content.json +10 -0
- package/dist/force-app/main/default/networks/appreactsampleb2x.network +60 -0
- package/dist/force-app/main/default/package.xml +20 -0
- package/dist/force-app/main/default/sites/appreactsampleb2x.site +31 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/.graphqlrc.yml +2 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/.prettierignore +9 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/.prettierrc +11 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/appreactsampleb2x.webapplication-meta.xml +7 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/build/vite.config.d.ts +2 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/build/vite.config.js +94 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/codegen.yml +12 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/e2e/app.spec.ts +24 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/eslint.config.js +141 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/index.html +13 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/package-lock.json +12805 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/package.json +57 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/playwright.config.ts +24 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/scripts/get-graphql-schema.mjs +68 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/scripts/rewrite-e2e-assets.mjs +23 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/graphql-operations-types.ts +129 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/utils/accounts.ts +33 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/utils/query/highRevenueAccountsQuery.graphql +29 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/app.tsx +41 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/appLayout.tsx +161 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/book.svg +3 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/copy.svg +4 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/rocket.svg +3 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/star.svg +3 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/images/codey-1.png +0 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/images/codey-2.png +0 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/images/codey-3.png +0 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/images/vibe-codey.svg +194 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/alert.tsx +65 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/button.tsx +54 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/card.tsx +77 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/field.tsx +111 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/index.ts +71 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/input.tsx +19 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/label.tsx +19 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/pagination.tsx +99 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/select.tsx +151 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/skeleton.tsx +7 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/spinner.tsx +26 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/table.tsx +114 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/components/ui/tabs.tsx +115 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/lib/utils.ts +6 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/About.tsx +8 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Application.tsx +101 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Dashboard.tsx +101 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/HelpCenter.tsx +29 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Home.tsx +30 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/Maintenance.tsx +132 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/NotFound.tsx +14 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/PropertyDetails.tsx +68 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/pages/PropertyListings.tsx +84 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/routes.tsx +62 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/styles/global.css +80 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/tsconfig.json +36 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/tsconfig.node.json +13 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/vite-env.d.ts +1 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/vite.config.ts +102 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/vitest-env.d.ts +2 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/vitest.config.ts +11 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/vitest.setup.ts +1 -0
- package/dist/force-app/main/default/webapplications/appreactsampleb2x/webapplication.json +7 -0
- package/dist/jest.config.js +6 -0
- package/dist/package.json +38 -0
- package/dist/scripts/apex/hello.apex +10 -0
- package/dist/scripts/soql/account.soql +6 -0
- package/dist/sfdx-project.json +12 -0
- package/package.json +28 -0
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "base-react-app",
|
|
3
|
+
"private": true,
|
|
4
|
+
"version": "1.0.0",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"scripts": {
|
|
7
|
+
"dev": "vite",
|
|
8
|
+
"build": "tsc -b && vite build",
|
|
9
|
+
"build:e2e": "npm run build && node scripts/rewrite-e2e-assets.mjs",
|
|
10
|
+
"lint": "eslint .",
|
|
11
|
+
"preview": "vite preview",
|
|
12
|
+
"test": "vitest",
|
|
13
|
+
"graphql:codegen": "graphql-codegen",
|
|
14
|
+
"graphql:schema": "node scripts/get-graphql-schema.mjs"
|
|
15
|
+
},
|
|
16
|
+
"dependencies": {
|
|
17
|
+
"@salesforce/sdk-data": "^1.11.2",
|
|
18
|
+
"@salesforce/webapp-experimental": "*",
|
|
19
|
+
"@tailwindcss/vite": "^4.1.17",
|
|
20
|
+
"react": "^19.2.0",
|
|
21
|
+
"react-dom": "^19.2.0",
|
|
22
|
+
"react-router": "^7.10.1",
|
|
23
|
+
"tailwindcss": "^4.1.17"
|
|
24
|
+
},
|
|
25
|
+
"devDependencies": {
|
|
26
|
+
"@eslint/js": "^9.39.1",
|
|
27
|
+
"@graphql-codegen/cli": "^6.1.0",
|
|
28
|
+
"@graphql-codegen/typescript": "^5.0.6",
|
|
29
|
+
"@graphql-codegen/typescript-operations": "^5.0.6",
|
|
30
|
+
"@graphql-eslint/eslint-plugin": "^4.1.0",
|
|
31
|
+
"@graphql-tools/utils": "^11.0.0",
|
|
32
|
+
"@playwright/test": "^1.49.0",
|
|
33
|
+
"@salesforce/vite-plugin-webapp-experimental": "*",
|
|
34
|
+
"@testing-library/jest-dom": "^6.6.3",
|
|
35
|
+
"@testing-library/react": "^16.1.0",
|
|
36
|
+
"@testing-library/user-event": "^14.5.2",
|
|
37
|
+
"@types/node": "^24.10.1",
|
|
38
|
+
"@types/react": "^19.2.5",
|
|
39
|
+
"@types/react-dom": "^19.2.3",
|
|
40
|
+
"@vitejs/plugin-react": "^5.1.1",
|
|
41
|
+
"@vitest/ui": "^4.0.17",
|
|
42
|
+
"eslint": "^9.39.1",
|
|
43
|
+
"eslint-plugin-react": "^7.37.2",
|
|
44
|
+
"eslint-plugin-react-hooks": "^7.0.1",
|
|
45
|
+
"eslint-plugin-react-refresh": "^0.4.24",
|
|
46
|
+
"globals": "^16.5.0",
|
|
47
|
+
"graphql": "^16.11.0",
|
|
48
|
+
"graphql-codegen-typescript-operation-types": "^2.0.2",
|
|
49
|
+
"jsdom": "^25.0.1",
|
|
50
|
+
"serve": "^14.2.5",
|
|
51
|
+
"typescript": "~5.9.3",
|
|
52
|
+
"typescript-eslint": "^8.46.4",
|
|
53
|
+
"vite": "^7.2.4",
|
|
54
|
+
"vite-plugin-graphql-codegen": "^3.6.3",
|
|
55
|
+
"vitest": "^4.0.17"
|
|
56
|
+
}
|
|
57
|
+
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { defineConfig, devices } from '@playwright/test';
|
|
2
|
+
|
|
3
|
+
const E2E_PORT = 5175;
|
|
4
|
+
|
|
5
|
+
export default defineConfig({
|
|
6
|
+
testDir: './e2e',
|
|
7
|
+
fullyParallel: true,
|
|
8
|
+
forbidOnly: !!process.env.CI,
|
|
9
|
+
retries: process.env.CI ? 2 : 0,
|
|
10
|
+
workers: process.env.CI ? 1 : undefined,
|
|
11
|
+
reporter: 'html',
|
|
12
|
+
use: {
|
|
13
|
+
baseURL: `http://localhost:${E2E_PORT}`,
|
|
14
|
+
trace: 'on-first-retry',
|
|
15
|
+
},
|
|
16
|
+
projects: [{ name: 'chromium', use: { ...devices['Desktop Chrome'] } }],
|
|
17
|
+
webServer: {
|
|
18
|
+
// Serve built dist/ with static server so e2e works in CI without SF org (vite preview runs plugin and can fail)
|
|
19
|
+
command: `npx serve dist -l ${E2E_PORT}`,
|
|
20
|
+
url: `http://localhost:${E2E_PORT}`,
|
|
21
|
+
reuseExistingServer: !process.env.CI,
|
|
22
|
+
timeout: process.env.CI ? 120_000 : 60_000,
|
|
23
|
+
},
|
|
24
|
+
});
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/scripts/get-graphql-schema.mjs
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Downloads the full GraphQL schema from a connected Salesforce org via introspection.
|
|
3
|
+
*
|
|
4
|
+
* Usage:
|
|
5
|
+
* npm run graphql:schema
|
|
6
|
+
* node scripts/get-graphql-schema.mjs [output-path]
|
|
7
|
+
*
|
|
8
|
+
* The default output path matches the schema location expected by codegen.yml
|
|
9
|
+
* and .graphqlrc.yml so that codegen and IDE tooling resolve it automatically.
|
|
10
|
+
*/
|
|
11
|
+
import { writeFileSync } from 'node:fs';
|
|
12
|
+
import { resolve } from 'node:path';
|
|
13
|
+
import { getOrgInfo } from '@salesforce/webapp-experimental/app';
|
|
14
|
+
import { buildClientSchema, getIntrospectionQuery, printSchema } from 'graphql';
|
|
15
|
+
import { pruneSchema } from '@graphql-tools/utils';
|
|
16
|
+
|
|
17
|
+
const DEFAULT_SCHEMA_PATH = '../../../../../schema.graphql';
|
|
18
|
+
|
|
19
|
+
async function executeSalesforceGraphQLQuery(query, variables, operationName) {
|
|
20
|
+
const {
|
|
21
|
+
rawInstanceUrl: instanceUrl,
|
|
22
|
+
apiVersion,
|
|
23
|
+
accessToken,
|
|
24
|
+
} = await getOrgInfo();
|
|
25
|
+
|
|
26
|
+
const targetUrl = `${instanceUrl}/services/data/v${apiVersion}/graphql`;
|
|
27
|
+
|
|
28
|
+
console.log(`Executing introspection query against ${targetUrl}`);
|
|
29
|
+
const response = await fetch(targetUrl, {
|
|
30
|
+
method: 'POST',
|
|
31
|
+
headers: {
|
|
32
|
+
Authorization: `Bearer ${accessToken}`,
|
|
33
|
+
'Content-Type': 'application/json',
|
|
34
|
+
'X-Chatter-Entity-Encoding': 'false',
|
|
35
|
+
},
|
|
36
|
+
body: JSON.stringify({ query, variables, operationName }),
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
if (!response.ok) {
|
|
40
|
+
const errorText = await response.text();
|
|
41
|
+
throw new Error(
|
|
42
|
+
`Salesforce GraphQL request failed: ${response.status} ${response.statusText} - ${errorText}`
|
|
43
|
+
);
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
return response.json();
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
try {
|
|
50
|
+
const outputPath = resolve(process.argv[2] || DEFAULT_SCHEMA_PATH);
|
|
51
|
+
|
|
52
|
+
const introspectionResult = await executeSalesforceGraphQLQuery(
|
|
53
|
+
getIntrospectionQuery(),
|
|
54
|
+
{},
|
|
55
|
+
'IntrospectionQuery'
|
|
56
|
+
);
|
|
57
|
+
|
|
58
|
+
const schema = buildClientSchema(introspectionResult.data);
|
|
59
|
+
const prunedSchema = pruneSchema(schema);
|
|
60
|
+
const sdl = printSchema(prunedSchema);
|
|
61
|
+
|
|
62
|
+
writeFileSync(outputPath, sdl);
|
|
63
|
+
|
|
64
|
+
console.log(`Schema saved to ${outputPath}`);
|
|
65
|
+
} catch (error) {
|
|
66
|
+
console.error('Error:', error.message);
|
|
67
|
+
process.exit(1);
|
|
68
|
+
}
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/scripts/rewrite-e2e-assets.mjs
ADDED
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Prepares dist/ for e2e: root-relative asset paths + SPA fallback for serve.
|
|
3
|
+
*/
|
|
4
|
+
import { readFileSync, writeFileSync } from 'node:fs';
|
|
5
|
+
import { join, dirname } from 'node:path';
|
|
6
|
+
import { fileURLToPath } from 'node:url';
|
|
7
|
+
|
|
8
|
+
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
9
|
+
const distDir = join(__dirname, '..', 'dist');
|
|
10
|
+
|
|
11
|
+
// Rewrite index.html so asset paths are root-relative (/assets/...)
|
|
12
|
+
const indexPath = join(distDir, 'index.html');
|
|
13
|
+
let html = readFileSync(indexPath, 'utf8');
|
|
14
|
+
html = html.replace(/(src|href)="[^"]*\/assets\//g, '$1="/assets/');
|
|
15
|
+
writeFileSync(indexPath, html);
|
|
16
|
+
|
|
17
|
+
// SPA fallback so /about, /non-existent-route etc. serve index.html
|
|
18
|
+
writeFileSync(
|
|
19
|
+
join(distDir, 'serve.json'),
|
|
20
|
+
JSON.stringify({
|
|
21
|
+
rewrites: [{ source: '**', destination: '/index.html' }],
|
|
22
|
+
})
|
|
23
|
+
);
|
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
export type Maybe<T> = T | null;
|
|
2
|
+
export type InputMaybe<T> = Maybe<T>;
|
|
3
|
+
export type Exact<T extends { [key: string]: unknown }> = {
|
|
4
|
+
[K in keyof T]: T[K];
|
|
5
|
+
};
|
|
6
|
+
export type MakeOptional<T, K extends keyof T> = Omit<T, K> & {
|
|
7
|
+
[SubKey in K]?: Maybe<T[SubKey]>;
|
|
8
|
+
};
|
|
9
|
+
export type MakeMaybe<T, K extends keyof T> = Omit<T, K> & {
|
|
10
|
+
[SubKey in K]: Maybe<T[SubKey]>;
|
|
11
|
+
};
|
|
12
|
+
export type MakeEmpty<
|
|
13
|
+
T extends { [key: string]: unknown },
|
|
14
|
+
K extends keyof T,
|
|
15
|
+
> = {
|
|
16
|
+
[_ in K]?: never;
|
|
17
|
+
};
|
|
18
|
+
export type Incremental<T> =
|
|
19
|
+
| T
|
|
20
|
+
| {
|
|
21
|
+
[P in keyof T]?: P extends ' $fragmentName' | '__typename' ? T[P] : never;
|
|
22
|
+
};
|
|
23
|
+
/** All built-in and custom scalars, mapped to their actual values */
|
|
24
|
+
export type Scalars = {
|
|
25
|
+
ID: { input: string; output: string };
|
|
26
|
+
String: { input: string; output: string };
|
|
27
|
+
Boolean: { input: boolean; output: boolean };
|
|
28
|
+
Int: { input: number; output: number };
|
|
29
|
+
Float: { input: number; output: number };
|
|
30
|
+
Base64: { input: any; output: any };
|
|
31
|
+
/** An arbitrary precision signed decimal */
|
|
32
|
+
BigDecimal: { input: any; output: any };
|
|
33
|
+
/** An arbitrary precision signed integer */
|
|
34
|
+
BigInteger: { input: any; output: any };
|
|
35
|
+
/** An 8-bit signed integer */
|
|
36
|
+
Byte: { input: any; output: any };
|
|
37
|
+
/** A UTF-16 code unit; a character on Unicode's BMP */
|
|
38
|
+
Char: { input: any; output: any };
|
|
39
|
+
Currency: { input: any; output: any };
|
|
40
|
+
Date: { input: any; output: any };
|
|
41
|
+
DateTime: { input: any; output: any };
|
|
42
|
+
Double: { input: any; output: any };
|
|
43
|
+
Email: { input: any; output: any };
|
|
44
|
+
EncryptedString: { input: any; output: any };
|
|
45
|
+
/** Can be set to an ID or a Reference to the result of another mutation operation. */
|
|
46
|
+
IdOrRef: { input: any; output: any };
|
|
47
|
+
JSON: { input: any; output: any };
|
|
48
|
+
Latitude: { input: any; output: any };
|
|
49
|
+
/** A 64-bit signed integer */
|
|
50
|
+
Long: { input: any; output: any };
|
|
51
|
+
LongTextArea: { input: any; output: any };
|
|
52
|
+
Longitude: { input: any; output: any };
|
|
53
|
+
MultiPicklist: { input: any; output: any };
|
|
54
|
+
Percent: { input: any; output: any };
|
|
55
|
+
PhoneNumber: { input: any; output: any };
|
|
56
|
+
Picklist: { input: any; output: any };
|
|
57
|
+
RichTextArea: { input: any; output: any };
|
|
58
|
+
/** A 16-bit signed integer */
|
|
59
|
+
Short: { input: any; output: any };
|
|
60
|
+
TextArea: { input: any; output: any };
|
|
61
|
+
Time: { input: any; output: any };
|
|
62
|
+
Url: { input: any; output: any };
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
export enum DataType {
|
|
66
|
+
Address = 'ADDRESS',
|
|
67
|
+
Anytype = 'ANYTYPE',
|
|
68
|
+
Base64 = 'BASE64',
|
|
69
|
+
Boolean = 'BOOLEAN',
|
|
70
|
+
Combobox = 'COMBOBOX',
|
|
71
|
+
Complexvalue = 'COMPLEXVALUE',
|
|
72
|
+
Currency = 'CURRENCY',
|
|
73
|
+
Date = 'DATE',
|
|
74
|
+
Datetime = 'DATETIME',
|
|
75
|
+
Double = 'DOUBLE',
|
|
76
|
+
Email = 'EMAIL',
|
|
77
|
+
Encryptedstring = 'ENCRYPTEDSTRING',
|
|
78
|
+
Int = 'INT',
|
|
79
|
+
Json = 'JSON',
|
|
80
|
+
Junctionidlist = 'JUNCTIONIDLIST',
|
|
81
|
+
Location = 'LOCATION',
|
|
82
|
+
Long = 'LONG',
|
|
83
|
+
Multipicklist = 'MULTIPICKLIST',
|
|
84
|
+
Percent = 'PERCENT',
|
|
85
|
+
Phone = 'PHONE',
|
|
86
|
+
Picklist = 'PICKLIST',
|
|
87
|
+
Reference = 'REFERENCE',
|
|
88
|
+
String = 'STRING',
|
|
89
|
+
Textarea = 'TEXTAREA',
|
|
90
|
+
Time = 'TIME',
|
|
91
|
+
Url = 'URL',
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
export enum FieldExtraTypeInfo {
|
|
95
|
+
ExternalLookup = 'EXTERNAL_LOOKUP',
|
|
96
|
+
ImageUrl = 'IMAGE_URL',
|
|
97
|
+
IndirectLookup = 'INDIRECT_LOOKUP',
|
|
98
|
+
Personname = 'PERSONNAME',
|
|
99
|
+
Plaintextarea = 'PLAINTEXTAREA',
|
|
100
|
+
Richtextarea = 'RICHTEXTAREA',
|
|
101
|
+
SwitchablePersonname = 'SWITCHABLE_PERSONNAME',
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
export enum ResultOrder {
|
|
105
|
+
Asc = 'ASC',
|
|
106
|
+
Desc = 'DESC',
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
export type GetHighRevenueAccountsQueryVariables = Exact<{
|
|
110
|
+
minRevenue?: InputMaybe<Scalars['Currency']['input']>;
|
|
111
|
+
}>;
|
|
112
|
+
|
|
113
|
+
export type GetHighRevenueAccountsQuery = {
|
|
114
|
+
uiapi: {
|
|
115
|
+
query: {
|
|
116
|
+
Account?: {
|
|
117
|
+
edges?: Array<{
|
|
118
|
+
node?: {
|
|
119
|
+
Id: string;
|
|
120
|
+
Name?: { value?: string | null } | null;
|
|
121
|
+
AnnualRevenue?: { value?: any | null } | null;
|
|
122
|
+
Industry?: { value?: any | null } | null;
|
|
123
|
+
Website?: { value?: any | null } | null;
|
|
124
|
+
} | null;
|
|
125
|
+
} | null> | null;
|
|
126
|
+
} | null;
|
|
127
|
+
};
|
|
128
|
+
};
|
|
129
|
+
};
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/api/utils/accounts.ts
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { executeGraphQL } from '@salesforce/webapp-experimental/api';
|
|
2
|
+
import HIGH_REVENUE_ACCOUNTS_QUERY from './query/highRevenueAccountsQuery.graphql?raw';
|
|
3
|
+
import type {
|
|
4
|
+
GetHighRevenueAccountsQuery,
|
|
5
|
+
GetHighRevenueAccountsQueryVariables,
|
|
6
|
+
} from '../graphql-operations-types';
|
|
7
|
+
|
|
8
|
+
type AccountNode = NonNullable<
|
|
9
|
+
NonNullable<
|
|
10
|
+
NonNullable<
|
|
11
|
+
NonNullable<
|
|
12
|
+
GetHighRevenueAccountsQuery['uiapi']['query']['Account']
|
|
13
|
+
>['edges']
|
|
14
|
+
>[number]
|
|
15
|
+
>['node']
|
|
16
|
+
>;
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Fetch accounts with annual revenue greater than the specified amount
|
|
20
|
+
*
|
|
21
|
+
* @param minRevenue - Minimum annual revenue threshold (default: 100000)
|
|
22
|
+
* @returns Array of accounts matching the criteria
|
|
23
|
+
*/
|
|
24
|
+
export async function getHighRevenueAccounts(
|
|
25
|
+
variables: GetHighRevenueAccountsQueryVariables
|
|
26
|
+
): Promise<(AccountNode | null | undefined)[]> {
|
|
27
|
+
const response = await executeGraphQL<GetHighRevenueAccountsQuery>(
|
|
28
|
+
HIGH_REVENUE_ACCOUNTS_QUERY,
|
|
29
|
+
variables
|
|
30
|
+
);
|
|
31
|
+
|
|
32
|
+
return response.uiapi?.query?.Account?.edges?.map(edge => edge?.node) || [];
|
|
33
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
query GetHighRevenueAccounts($minRevenue: Currency) {
|
|
2
|
+
uiapi {
|
|
3
|
+
query {
|
|
4
|
+
Account(
|
|
5
|
+
where: { AnnualRevenue: { gt: $minRevenue } }
|
|
6
|
+
orderBy: { AnnualRevenue: { order: DESC } }
|
|
7
|
+
first: 50
|
|
8
|
+
) {
|
|
9
|
+
edges {
|
|
10
|
+
node {
|
|
11
|
+
Id
|
|
12
|
+
Name {
|
|
13
|
+
value
|
|
14
|
+
}
|
|
15
|
+
AnnualRevenue {
|
|
16
|
+
value
|
|
17
|
+
}
|
|
18
|
+
Industry {
|
|
19
|
+
value
|
|
20
|
+
}
|
|
21
|
+
Website {
|
|
22
|
+
value
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { createBrowserRouter, RouterProvider } from "react-router";
|
|
2
|
+
import { routes } from "@/routes";
|
|
3
|
+
import { StrictMode, Component, type ReactNode } from "react";
|
|
4
|
+
import { createRoot } from "react-dom/client";
|
|
5
|
+
import "./styles/global.css";
|
|
6
|
+
|
|
7
|
+
class ErrorBoundary extends Component<
|
|
8
|
+
{ children: ReactNode },
|
|
9
|
+
{ hasError: boolean; error: Error | null }
|
|
10
|
+
> {
|
|
11
|
+
state = { hasError: false, error: null as Error | null };
|
|
12
|
+
static getDerivedStateFromError(error: Error) {
|
|
13
|
+
return { hasError: true, error };
|
|
14
|
+
}
|
|
15
|
+
render() {
|
|
16
|
+
if (this.state.hasError && this.state.error) {
|
|
17
|
+
return (
|
|
18
|
+
<div className="mx-auto max-w-[600px] p-8 font-sans">
|
|
19
|
+
<h1 className="text-xl text-destructive">Something went wrong</h1>
|
|
20
|
+
<pre className="mt-2 overflow-auto rounded-md bg-destructive/10 p-4 text-sm">
|
|
21
|
+
{this.state.error.message}
|
|
22
|
+
</pre>
|
|
23
|
+
</div>
|
|
24
|
+
);
|
|
25
|
+
}
|
|
26
|
+
return this.props.children;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
const baseUrl = import.meta.env.BASE_URL ?? "/";
|
|
31
|
+
const router = createBrowserRouter(routes, { basename: baseUrl === "/" ? undefined : baseUrl });
|
|
32
|
+
const rootEl = document.getElementById("root");
|
|
33
|
+
if (rootEl) {
|
|
34
|
+
createRoot(rootEl).render(
|
|
35
|
+
<StrictMode>
|
|
36
|
+
<ErrorBoundary>
|
|
37
|
+
<RouterProvider router={router} />
|
|
38
|
+
</ErrorBoundary>
|
|
39
|
+
</StrictMode>,
|
|
40
|
+
);
|
|
41
|
+
}
|
|
@@ -0,0 +1,161 @@
|
|
|
1
|
+
import { useState } from "react";
|
|
2
|
+
import { Outlet, NavLink } from "react-router";
|
|
3
|
+
import { Button } from "./components/ui/button";
|
|
4
|
+
import { cn } from "./lib/utils";
|
|
5
|
+
import {
|
|
6
|
+
Home,
|
|
7
|
+
Search,
|
|
8
|
+
BarChart3,
|
|
9
|
+
Wrench,
|
|
10
|
+
HelpCircle,
|
|
11
|
+
Menu,
|
|
12
|
+
Heart,
|
|
13
|
+
Bell,
|
|
14
|
+
Building2,
|
|
15
|
+
} from "lucide-react";
|
|
16
|
+
|
|
17
|
+
const SIDEBAR_WIDTH = 200;
|
|
18
|
+
const FLOAT_INSET = 20;
|
|
19
|
+
const FLOAT_GAP = 20;
|
|
20
|
+
|
|
21
|
+
function AppShell() {
|
|
22
|
+
const [navHidden, setNavHidden] = useState(false);
|
|
23
|
+
|
|
24
|
+
return (
|
|
25
|
+
<div className="flex min-h-screen flex-col">
|
|
26
|
+
<header
|
|
27
|
+
className="flex shrink-0 items-center justify-between bg-primary px-6 py-3 text-primary-foreground"
|
|
28
|
+
role="banner"
|
|
29
|
+
>
|
|
30
|
+
<div className="flex items-center gap-3">
|
|
31
|
+
<Button
|
|
32
|
+
type="button"
|
|
33
|
+
variant="ghost"
|
|
34
|
+
size="icon"
|
|
35
|
+
className="min-h-11 min-w-11 text-primary-foreground hover:bg-primary-foreground/20"
|
|
36
|
+
aria-label={navHidden ? "Show menu" : "Hide menu"}
|
|
37
|
+
onClick={() => setNavHidden((h) => !h)}
|
|
38
|
+
>
|
|
39
|
+
<Menu className="size-6" aria-hidden />
|
|
40
|
+
</Button>
|
|
41
|
+
<div className="flex size-8 items-center justify-center">
|
|
42
|
+
<Building2 className="size-7" aria-hidden />
|
|
43
|
+
</div>
|
|
44
|
+
<span className="text-xl font-semibold tracking-wide">ZENLEASE</span>
|
|
45
|
+
</div>
|
|
46
|
+
<div className="flex items-center gap-4">
|
|
47
|
+
<Button
|
|
48
|
+
type="button"
|
|
49
|
+
variant="ghost"
|
|
50
|
+
size="icon"
|
|
51
|
+
className="text-primary-foreground hover:bg-primary-foreground/20"
|
|
52
|
+
aria-label="Favorites"
|
|
53
|
+
>
|
|
54
|
+
<Heart className="size-5" aria-hidden />
|
|
55
|
+
</Button>
|
|
56
|
+
<Button
|
|
57
|
+
type="button"
|
|
58
|
+
variant="ghost"
|
|
59
|
+
size="icon"
|
|
60
|
+
className="text-primary-foreground hover:bg-primary-foreground/20"
|
|
61
|
+
aria-label="Notifications"
|
|
62
|
+
>
|
|
63
|
+
<Bell className="size-5" aria-hidden />
|
|
64
|
+
</Button>
|
|
65
|
+
<div className="flex items-center gap-2">
|
|
66
|
+
<div className="size-9 shrink-0 rounded-full bg-primary-foreground/25" aria-hidden />
|
|
67
|
+
<span className="text-sm font-medium">SARAH</span>
|
|
68
|
+
</div>
|
|
69
|
+
</div>
|
|
70
|
+
</header>
|
|
71
|
+
<div className="relative flex min-h-0 flex-1">
|
|
72
|
+
{!navHidden && (
|
|
73
|
+
<nav
|
|
74
|
+
className="absolute left-5 top-5 bottom-5 z-10 flex w-[200px] flex-col items-start gap-1 overflow-hidden rounded-2xl border border-border bg-card p-4 py-2 shadow-lg"
|
|
75
|
+
aria-label="Main navigation"
|
|
76
|
+
>
|
|
77
|
+
<NavLink
|
|
78
|
+
to="/"
|
|
79
|
+
end
|
|
80
|
+
className={({ isActive }) =>
|
|
81
|
+
cn(
|
|
82
|
+
"flex min-h-11 w-full flex-shrink-0 items-center justify-start gap-3 rounded-xl px-3 py-2 text-muted-foreground no-underline transition-colors",
|
|
83
|
+
isActive && "bg-primary text-primary-foreground",
|
|
84
|
+
)
|
|
85
|
+
}
|
|
86
|
+
aria-label="Home"
|
|
87
|
+
>
|
|
88
|
+
<Home className="size-[22px] shrink-0" aria-hidden />
|
|
89
|
+
<span className="text-sm font-medium">Home</span>
|
|
90
|
+
</NavLink>
|
|
91
|
+
<NavLink
|
|
92
|
+
to="/properties"
|
|
93
|
+
className={({ isActive }) =>
|
|
94
|
+
cn(
|
|
95
|
+
"flex min-h-11 w-full flex-shrink-0 items-center justify-start gap-3 rounded-xl px-3 py-2 text-muted-foreground no-underline transition-colors",
|
|
96
|
+
isActive && "bg-primary text-primary-foreground",
|
|
97
|
+
)
|
|
98
|
+
}
|
|
99
|
+
aria-label="Property Search"
|
|
100
|
+
>
|
|
101
|
+
<Search className="size-[22px] shrink-0" aria-hidden />
|
|
102
|
+
<span className="text-sm font-medium">Property Search</span>
|
|
103
|
+
</NavLink>
|
|
104
|
+
<NavLink
|
|
105
|
+
to="/dashboard"
|
|
106
|
+
className={({ isActive }) =>
|
|
107
|
+
cn(
|
|
108
|
+
"flex min-h-11 w-full flex-shrink-0 items-center justify-start gap-3 rounded-xl px-3 py-2 text-muted-foreground no-underline transition-colors",
|
|
109
|
+
isActive && "bg-primary text-primary-foreground",
|
|
110
|
+
)
|
|
111
|
+
}
|
|
112
|
+
aria-label="Dashboard"
|
|
113
|
+
>
|
|
114
|
+
<BarChart3 className="size-[22px] shrink-0" aria-hidden />
|
|
115
|
+
<span className="text-sm font-medium">Dashboard</span>
|
|
116
|
+
</NavLink>
|
|
117
|
+
<NavLink
|
|
118
|
+
to="/maintenance"
|
|
119
|
+
className={({ isActive }) =>
|
|
120
|
+
cn(
|
|
121
|
+
"flex min-h-11 w-full flex-shrink-0 items-center justify-start gap-3 rounded-xl px-3 py-2 text-muted-foreground no-underline transition-colors",
|
|
122
|
+
isActive && "bg-primary text-primary-foreground",
|
|
123
|
+
)
|
|
124
|
+
}
|
|
125
|
+
aria-label="Maintenance"
|
|
126
|
+
>
|
|
127
|
+
<Wrench className="size-[22px] shrink-0" aria-hidden />
|
|
128
|
+
<span className="text-sm font-medium">Maintenance</span>
|
|
129
|
+
</NavLink>
|
|
130
|
+
<NavLink
|
|
131
|
+
to="/help"
|
|
132
|
+
className={({ isActive }) =>
|
|
133
|
+
cn(
|
|
134
|
+
"flex min-h-11 w-full flex-shrink-0 items-center justify-start gap-3 rounded-xl px-3 py-2 text-muted-foreground no-underline transition-colors",
|
|
135
|
+
isActive && "bg-primary text-primary-foreground",
|
|
136
|
+
)
|
|
137
|
+
}
|
|
138
|
+
aria-label="Help Center"
|
|
139
|
+
>
|
|
140
|
+
<HelpCircle className="size-[22px] shrink-0" aria-hidden />
|
|
141
|
+
<span className="text-sm font-medium">Help Center</span>
|
|
142
|
+
</NavLink>
|
|
143
|
+
</nav>
|
|
144
|
+
)}
|
|
145
|
+
<main
|
|
146
|
+
className="min-h-full flex-1 overflow-auto bg-muted/30 p-6 transition-[margin-left] duration-200 ease-[cubic-bezier(0.4,0,0.2,1)]"
|
|
147
|
+
style={{
|
|
148
|
+
marginLeft: navHidden ? 0 : FLOAT_INSET + SIDEBAR_WIDTH + FLOAT_GAP,
|
|
149
|
+
}}
|
|
150
|
+
role="main"
|
|
151
|
+
>
|
|
152
|
+
<Outlet />
|
|
153
|
+
</main>
|
|
154
|
+
</div>
|
|
155
|
+
</div>
|
|
156
|
+
);
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
export default function AppLayout() {
|
|
160
|
+
return <AppShell />;
|
|
161
|
+
}
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/book.svg
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
<svg width="14" height="12" viewBox="0 0 14 12" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<path d="M13.4935 0.000188828L13.9735 0.533522V10.5069L13.4935 11.0402H8.21348L7.36015 11.8935H6.61348L5.76015 11.0402H0.48015L0.000149727 10.5069V0.533522L0.48015 0.000188828H5.97348L6.34682 0.160189L6.98682 0.800188L7.62682 0.160189L8.00015 0.000188828H13.4935ZM6.50682 10.3469V1.76019L5.76015 1.01352H1.01348V10.0269H5.97348L6.29348 10.1869L6.50682 10.3469ZM13.0135 10.0269V1.01352H8.21348L7.52015 1.70685V10.2935L7.62682 10.1869L8.00015 10.0269H13.0135ZM5.01348 3.04019V4.00019H1.97348V3.04019H5.01348ZM5.01348 7.04019V8.00019H1.97348V7.04019H5.01348ZM1.97348 5.01352V6.02686H5.01348V5.01352H1.97348ZM12.0001 3.04019V4.00019H9.01348V3.04019H12.0001ZM9.01348 5.01352V6.02686H12.0001V5.01352H9.01348ZM9.01348 7.04019V8.00019H12.0001V7.04019H9.01348Z" fill="#0250D9"/>
|
|
3
|
+
</svg>
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/copy.svg
ADDED
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
<svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<path fill-rule="evenodd" clip-rule="evenodd" d="M5 5L6.25 3.75H13.0175L17.5 8.2325V17.5L16.25 18.75H6.25L5 17.5V5ZM16.25 8.75L12.5 5H6.25V17.5H16.25V8.75Z" fill="#2E2E2E"/>
|
|
3
|
+
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.75 1.25L2.5 2.5V15L3.75 16.25V2.5H11.7675L10.5175 1.25H3.75Z" fill="#2E2E2E"/>
|
|
4
|
+
</svg>
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/rocket.svg
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
<svg width="14" height="14" viewBox="0 0 14 14" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<path d="M13.4935 0.000149727L13.9735 0.480149C13.9735 2.15126 13.5646 3.80459 12.7468 5.44015C12.0713 6.7557 11.1468 8.05348 9.97348 9.33348V13.4935L9.49348 13.9735H6.50682L6.13348 13.8668L0.16015 7.84015L0.000149727 7.46682V4.48015L0.48015 4.00015H4.64015C5.92015 2.82682 7.21793 1.90237 8.53348 1.22682C10.169 0.409039 11.8224 0.000149727 13.4935 0.000149727ZM1.01348 4.96015V7.30682L1.38682 7.68015C2.06237 6.72015 2.80904 5.81348 3.62682 4.96015H1.01348ZM6.66682 12.9601H8.96015V10.3468C8.14237 11.1646 7.25348 11.9113 6.29348 12.5868L6.66682 12.9601ZM5.54682 11.8401C6.40015 11.2713 7.23571 10.6135 8.05348 9.86682C9.33348 8.62237 10.3824 7.36015 11.2002 6.08015C12.2668 4.37348 12.8535 2.68459 12.9601 1.01348C11.289 1.12015 9.60015 1.70682 7.89348 2.77348C6.61348 3.59126 5.35126 4.64015 4.10682 5.92015C3.36015 6.73793 2.70237 7.57348 2.13348 8.42682L5.54682 11.8401ZM2.98682 13.9735H0.000149727V10.9868H1.01348V12.9601H2.98682V13.9735ZM9.76015 6.29348C9.51126 6.64904 9.17348 6.88015 8.74682 6.98682C8.35571 7.05793 7.98237 6.98682 7.62682 6.77348C7.30682 6.52459 7.09348 6.20459 6.98682 5.81348C6.91571 5.38682 6.98682 5.01348 7.20015 4.69348C7.44904 4.33793 7.76904 4.12459 8.16015 4.05348C8.58682 3.94682 8.96015 4.01793 9.28015 4.26682C9.63571 4.48015 9.84904 4.80015 9.92015 5.22682C10.0268 5.61793 9.97348 5.97348 9.76015 6.29348Z" fill="#066AFE"/>
|
|
3
|
+
</svg>
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/icons/star.svg
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
<svg width="14" height="13" viewBox="0 0 14 13" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<path d="M5.70684 0.533125C5.8135 0.319791 5.9735 0.177569 6.18684 0.106458C6.40017 0.0353467 6.6135 0.0353467 6.82684 0.106458C7.04017 0.177569 7.20017 0.319791 7.30684 0.533125L8.8535 3.62646L12.2135 4.10646C12.4624 4.14201 12.6579 4.26646 12.8002 4.47979C12.9424 4.65757 13.0135 4.8709 13.0135 5.11979C13.0135 5.33312 12.9246 5.5109 12.7468 5.65312L10.2935 8.05312L10.8802 11.4665C10.9157 11.6798 10.8624 11.8931 10.7202 12.1065C10.5779 12.2842 10.4002 12.4087 10.1868 12.4798C9.9735 12.5509 9.76017 12.5331 9.54684 12.4265L6.50684 10.8265L3.46684 12.4265C3.2535 12.5331 3.04017 12.5509 2.82684 12.4798C2.6135 12.4087 2.43572 12.2842 2.2935 12.1065C2.15128 11.8931 2.09795 11.6798 2.1335 11.4665L2.72017 8.05312L0.266836 5.65312C0.0890582 5.5109 0.000169277 5.33312 0.000169277 5.11979C0.000169277 4.8709 0.0712804 4.65757 0.213503 4.47979C0.355725 4.26646 0.55128 4.14201 0.800169 4.10646L4.16017 3.62646L5.70684 0.533125ZM6.50684 1.17312L5.06684 4.10646C4.92461 4.3909 4.6935 4.56868 4.3735 4.63979L1.12017 5.06646L3.46684 7.35979C3.71572 7.60868 3.80461 7.87535 3.7335 8.15979L3.20017 11.4131L6.08017 9.86646C6.36461 9.72424 6.64906 9.72424 6.9335 9.86646L9.8135 11.4131L9.28017 8.15979C9.24461 7.87535 9.3335 7.60868 9.54684 7.35979L11.8935 5.06646L8.64017 4.63979C8.32017 4.56868 8.08906 4.3909 7.94684 4.10646L6.50684 1.17312Z" fill="#066AFE"/>
|
|
3
|
+
</svg>
|
package/dist/force-app/main/default/webapplications/appreactsampleb2x/src/assets/images/codey-1.png
ADDED
|
Binary file
|