diff --git a/genstudio-mlr-claims-app/package-lock.json b/genstudio-mlr-claims-app/package-lock.json index 95458bc..1c6a491 100644 --- a/genstudio-mlr-claims-app/package-lock.json +++ b/genstudio-mlr-claims-app/package-lock.json @@ -9,7 +9,7 @@ "version": "0.2.0", "dependencies": { "@adobe/aio-sdk": "^6.0.0", - "@adobe/genstudio-extensibility-sdk": "^4.4.0", + "@adobe/genstudio-extensibility-sdk": "^4.5.0", "@adobe/uix-guest": "^1.0.0", "@react-spectrum/s2": "^0.9.0", "core-js": "^3.6.4", @@ -779,9 +779,9 @@ } }, "node_modules/@adobe/genstudio-extensibility-sdk": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/@adobe/genstudio-extensibility-sdk/-/genstudio-extensibility-sdk-4.4.0.tgz", - "integrity": "sha512-IeRkMH1yoFOTeE+ZoWPRtE7LKjCjeeuNVGAT7XHVgGL0a8hwgJV7f4mhLNRNYzVjoldKrcleHRuhk9yeTpoFwQ==", + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/@adobe/genstudio-extensibility-sdk/-/genstudio-extensibility-sdk-4.5.0.tgz", + "integrity": "sha512-B8a2T4pybz9rayvq17Ojb/GjDqB5/AFhKc0MTKYnKcjnwgxUDYZkSHdfJ5YmdBktBz2PEg2etH1ZOwdrobM+YA==", "license": "Apache-2.0", "dependencies": { "@adobe/uix-core": "^1.0.0", diff --git a/genstudio-mlr-claims-app/package.json b/genstudio-mlr-claims-app/package.json index dcc198f..52114e9 100644 --- a/genstudio-mlr-claims-app/package.json +++ b/genstudio-mlr-claims-app/package.json @@ -3,7 +3,7 @@ "version": "0.2.0", "private": true, "dependencies": { - "@adobe/genstudio-extensibility-sdk": "^4.4.0", + "@adobe/genstudio-extensibility-sdk": "^4.5.0", "@adobe/uix-guest": "^1.0.0", "@adobe/aio-sdk": "^6.0.0", "@react-spectrum/s2": "^0.9.0", diff --git a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/Constants.ts b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/Constants.ts index 839ac2d..8115591 100644 --- a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/Constants.ts +++ b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/Constants.ts @@ -17,6 +17,7 @@ export const ICON_DATA_URI: string = export const VALIDATION_PANEL_ROUTE: string = "/validation-panel"; export const PROMPT_DIALOG_ROUTE: string = "/prompt-dialog"; +export const FRAGMENT_SWAP_DIALOG_ROUTE: string = "/fragment-swap-dialog"; /** * App metadata object diff --git a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/App.tsx b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/App.tsx index 2c33362..c754991 100644 --- a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/App.tsx +++ b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/App.tsx @@ -18,7 +18,12 @@ import { style } from "@react-spectrum/s2/style" with {type: 'macro'}; import ExtensionRegistration from "./ExtensionRegistration"; import ValidationPanel from "../components/ValidationPanel"; import PromptDialog from "../components/PromptDialog"; -import { PROMPT_DIALOG_ROUTE, VALIDATION_PANEL_ROUTE } from "../Constants"; +import FragmentSwapDialog from "../components/FragmentSwapDialog"; +import { + FRAGMENT_SWAP_DIALOG_ROUTE, + PROMPT_DIALOG_ROUTE, + VALIDATION_PANEL_ROUTE, +} from "../Constants"; const ErrorFallback = () => Something went wrong!; @@ -35,6 +40,10 @@ const App = (): React.JSX.Element => { } /> } /> } /> + } + /> diff --git a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/ExtensionRegistration.tsx b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/ExtensionRegistration.tsx index fa445c8..bc8939d 100644 --- a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/ExtensionRegistration.tsx +++ b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/app/ExtensionRegistration.tsx @@ -21,10 +21,12 @@ import { APP_METADATA, VALIDATION_PANEL_ROUTE, PROMPT_DIALOG_ROUTE, + FRAGMENT_SWAP_DIALOG_ROUTE, } from "../Constants"; import { App, AppMetadata, + FragmentSwapExtensionService, PromptExtensionService, ValidationExtensionService, Toggle, @@ -88,6 +90,26 @@ const ExtensionRegistration = (): React.JSX.Element => { ]; }, }, + fragmentSwapExtension: { + getToggles: async (id: string): Promise => { + return [ + { + metadata: getAppMetadata(id), + onClick: async () => { + FragmentSwapExtensionService.open(guestConnection as any, id); + }, + }, + ]; + }, + getApps(id: string): App[] { + return [ + { + metadata: getAppMetadata(id), + url: `#${FRAGMENT_SWAP_DIALOG_ROUTE}`, + }, + ]; + }, + }, }, }); }; diff --git a/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/components/FragmentSwapDialog/index.tsx b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/components/FragmentSwapDialog/index.tsx new file mode 100644 index 0000000..24acbc6 --- /dev/null +++ b/genstudio-mlr-claims-app/src/genstudiopem/web-src/src/components/FragmentSwapDialog/index.tsx @@ -0,0 +1,110 @@ +/* + * Copyright 2026 Adobe. All rights reserved. + * This file is licensed to you under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. You may obtain a copy + * of the License at http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software distributed under + * the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTATIONS + * OF ANY KIND, either express or implied. See the License for the specific language + * governing permissions and limitations under the License. + */ + +import { FragmentSwapExtensionService } from "@adobe/genstudio-extensibility-sdk"; +import { Heading, ProgressCircle, Text } from "@react-spectrum/s2"; +import { style } from "@react-spectrum/s2/style" with { type: "macro" }; +import React, { useMemo, useState } from "react"; +import { EXTENSION_ID } from "../../Constants"; +import { useAuth, useClaimActions, useGuestConnection } from "../../hooks"; + +const listStyle = style({ + display: "flex", + flexDirection: "column", + gap: 8, + marginTop: 12, +}); + +const itemStyle = style({ + padding: 12, + borderRadius: "default", + borderWidth: 2, + borderStyle: "solid", + cursor: "pointer", + textAlign: "start", +}); + +export default function FragmentSwapDialog(): React.JSX.Element { + const guestConnection = useGuestConnection(EXTENSION_ID); + const auth = useAuth(guestConnection); + const { claimLibraries, isLoadingClaims, error } = useClaimActions(auth); + const [selectedClaimId, setSelectedClaimId] = useState(null); + + const flatClaims = useMemo(() => { + return (claimLibraries ?? []).flatMap((lib) => + lib.claims.map((claim) => ({ + libraryName: lib.name, + claim, + })), + ); + }, [claimLibraries]); + + const handleClaimSelect = (claimId: string, description: string): void => { + setSelectedClaimId(claimId); + if (guestConnection) { + FragmentSwapExtensionService.setSwapValue(guestConnection, description); + } + }; + + if (isLoadingClaims) { + return ( + + + + ); + } + + return ( + + Pick a claim to swap in + {error && {error}} + + {flatClaims.length === 0 && No claims available.} + {flatClaims.map(({ libraryName, claim }) => { + const isSelected = claim.id === selectedClaimId; + return ( + handleClaimSelect(claim.id, claim.description)} + className={itemStyle} + style={{ + borderColor: isSelected ? "#1473e6" : "#d0d0d0", + backgroundColor: isSelected ? "#e8f0fe" : "white", + fontWeight: isSelected ? 600 : 400, + }} + > + + {libraryName} + {claim.description} + + + ); + })} + + + ); +}