diff --git a/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretEditRow.tsx b/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretEditRow.tsx index ddb9a99d1..d3017b202 100644 --- a/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretEditRow.tsx +++ b/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretEditRow.tsx @@ -87,6 +87,7 @@ export const SecretEditRow = ({ const { permission } = useProjectPermission(); const [isDeleting, setIsDeleting] = useToggle(); + const [isSecretBlurFocus, setIsSecretBlurFocus] = useToggle(false); const [isModalOpen, setIsModalOpen] = useState(false); const toggleModal = useCallback(() => { @@ -124,7 +125,14 @@ export const SecretEditRow = ({ ); } } - reset({ value }); + if (secretValueHidden) { + setTimeout(() => { + reset({ value: defaultValue || null }); + }, 0); + setIsSecretBlurFocus.off(); + } else { + reset({ value }); + } }; const canReadSecretValue = hasSecretReadValueOrDescribePermission( @@ -132,6 +140,22 @@ export const SecretEditRow = ({ ProjectPermissionSecretActions.ReadValue ); + const canEditSecretValue = permission.can( + ProjectPermissionSecretActions.Edit, + subject(ProjectPermissionSub.Secrets, { + environment, + secretPath, + secretName, + secretTags: ["*"] + }) + ); + + const handleSecretBlurClick = () => { + if (canEditSecretValue) { + setIsSecretBlurFocus.toggle(); + } + }; + const handleDeleteSecret = useCallback(async () => { setIsDeleting.on(); setIsModalOpen(false); @@ -155,8 +179,17 @@ export const SecretEditRow = ({ />
- {secretValueHidden ? ( - + {secretValueHidden && !isSecretBlurFocus ? ( + // eslint-disable-next-line jsx-a11y/click-events-have-key-events, jsx-a11y/no-static-element-interactions +
setIsSecretBlurFocus.off()} + > + +
) : ( )} /> diff --git a/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretOverviewTableRow.tsx b/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretOverviewTableRow.tsx index 15e6753f3..78afaa021 100644 --- a/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretOverviewTableRow.tsx +++ b/frontend/src/pages/secret-manager/OverviewPage/components/SecretOverviewTableRow/SecretOverviewTableRow.tsx @@ -1,3 +1,4 @@ +import { subject } from "@casl/ability"; import { faCircle } from "@fortawesome/free-regular-svg-icons"; import { faAngleDown, @@ -14,6 +15,11 @@ import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; import { twMerge } from "tailwind-merge"; import { Button, Checkbox, TableContainer, Td, Tooltip, Tr } from "@app/components/v2"; +import { useProjectPermission } from "@app/context"; +import { + ProjectPermissionSecretActions, + ProjectPermissionSub +} from "@app/context/ProjectPermissionContext/types"; import { useToggle } from "@app/hooks"; import { SecretType, SecretV3RawSanitized } from "@app/hooks/api/secrets/types"; import { WorkspaceEnv } from "@app/hooks/api/types"; @@ -64,6 +70,28 @@ export const SecretOverviewTableRow = ({ const totalCols = environments.length + 1; // secret key row const [isSecretVisible, setIsSecretVisible] = useToggle(); + const { permission } = useProjectPermission(); + + const getDefaultValue = ( + secret: SecretV3RawSanitized | undefined, + importedSecret: { secret?: SecretV3RawSanitized } | undefined + ) => { + const canEditSecretValue = permission.can( + ProjectPermissionSecretActions.Edit, + subject(ProjectPermissionSub.Secrets, { + environment: secret?.env || "", + secretPath: secret?.path || "", + secretName: secret?.key || "", + secretTags: ["*"] + }) + ); + + if (secret?.secretValueHidden) { + return canEditSecretValue ? "" : ""; + } + return secret?.valueOverride || secret?.value || importedSecret?.secret?.value || ""; + }; + return ( <> setIsFormExpanded.toggle()} className="group"> @@ -228,13 +256,7 @@ export const SecretOverviewTableRow = ({ isVisible={isSecretVisible} secretName={secretKey} secretValueHidden={secret?.secretValueHidden || false} - defaultValue={ - secret?.secretValueHidden - ? "" - : secret?.valueOverride || - secret?.value || - importedSecret?.secret?.value - } + defaultValue={getDefaultValue(secret, importedSecret)} secretId={secret?.id} isOverride={Boolean(secret?.valueOverride)} isImportedSecret={isImportedSecret} diff --git a/frontend/src/pages/secret-manager/SecretDashboardPage/components/SecretListView/SecretItem.tsx b/frontend/src/pages/secret-manager/SecretDashboardPage/components/SecretListView/SecretItem.tsx index 5c431427c..135f1868c 100644 --- a/frontend/src/pages/secret-manager/SecretDashboardPage/components/SecretListView/SecretItem.tsx +++ b/frontend/src/pages/secret-manager/SecretDashboardPage/components/SecretListView/SecretItem.tsx @@ -94,6 +94,24 @@ export const SecretItem = memo( const { currentWorkspace } = useWorkspace(); const { permission } = useProjectPermission(); const { isRotatedSecret } = secret; + const [isSecretBlurFocus, setIsSecretBlurFocus] = useToggle(false); + + const canEditSecretValue = permission.can( + ProjectPermissionSecretActions.Edit, + subject(ProjectPermissionSub.Secrets, { + environment, + secretPath, + secretName: secret.key, + secretTags: ["*"] + }) + ); + + const getDefaultValue = () => { + if (secret.secretValueHidden) { + return canEditSecretValue ? "" : ""; + } + return secret.valueOverride || secret.value || ""; + }; const { handleSubmit, @@ -108,11 +126,11 @@ export const SecretItem = memo( } = useForm({ defaultValues: { ...secret, - value: secret.secretValueHidden ? "" : secret.value + value: getDefaultValue() }, values: { ...secret, - value: secret.secretValueHidden ? "" : secret.value + value: getDefaultValue() }, resolver: zodResolver(formSchema) }); @@ -154,6 +172,7 @@ export const SecretItem = memo( secretTags: selectedTagSlugs }) ); + const { secretValueHidden } = secret; const [isSecValueCopied, setIsSecValueCopied] = useToggle(false); @@ -169,6 +188,12 @@ export const SecretItem = memo( overrideAction === SecretActionType.Created || overrideAction === SecretActionType.Modified; const hasTagsApplied = Boolean(fields.length); + const handleSecretBlurClick = () => { + if (canEditSecretValue) { + setIsSecretBlurFocus.toggle(); + } + }; + const handleOverrideClick = () => { if (isOverriden) { // override need not be flagged delete if it was never saved in server @@ -301,8 +326,17 @@ export const SecretItem = memo( /> )} /> - ) : secretValueHidden ? ( - + ) : secretValueHidden && !isSecretBlurFocus ? ( + // eslint-disable-next-line jsx-a11y/click-events-have-key-events, jsx-a11y/no-static-element-interactions +
setIsSecretBlurFocus.off()} + > + +
) : ( " : undefined} containerClassName="py-1.5 rounded-md transition-all" /> )}