add new modal to compare secrets across environments

This commit is contained in:
Mohammed
2023-02-03 22:33:39 +01:00
parent 76d0127029
commit 1781b71399
2 changed files with 119 additions and 16 deletions
@@ -0,0 +1,75 @@
import { SetStateAction, useEffect, useState } from 'react';
import { WorkspaceEnv } from '~/pages/dashboard/[id]';
import getSecretsForProject from '../utilities/secrets/getSecretsForProject';
import { Modal, ModalContent } from '../v2';
interface Secrets {
label: string;
secret: string;
}
interface CompareSecretsModalProps {
compareModal: boolean;
setCompareModal: React.Dispatch<SetStateAction<boolean>>;
selectedEnv: WorkspaceEnv;
workspaceEnvs: WorkspaceEnv[];
workspaceId: string;
currentSecret: {
key: string;
value: string;
};
}
const CompareSecretsModal = ({
compareModal,
setCompareModal,
selectedEnv,
workspaceEnvs,
workspaceId,
currentSecret
}: CompareSecretsModalProps) => {
const [secrets, setSecrets] = useState<Secrets[]>([]);
const getEnvSecrets = async () => {
const workspaceEnvironments = workspaceEnvs.filter((env) => env !== selectedEnv);
const newSecrets = await Promise.all(
workspaceEnvironments.map(async (env) => {
const allSecrets = await getSecretsForProject({ env: env.slug, workspaceId });
const secret =
allSecrets.find((item) => item.key === currentSecret.key)?.value ?? 'Not found';
return { label: env.name, secret };
})
);
setSecrets([{ label: selectedEnv.name, secret: currentSecret.value }, ...newSecrets]);
};
useEffect(() => {
if (compareModal) {
(async () => {
await getEnvSecrets();
})();
}
}, [compareModal]);
return (
<Modal isOpen={compareModal} onOpenChange={setCompareModal}>
<ModalContent title={currentSecret?.key} onOpenAutoFocus={(e) => e.preventDefault()}>
<div className="space-y-4">
{secrets.map((item) => (
<div key={`${currentSecret.key}${item.label}`} className="space-y-1">
<p className="text-sm text-bunker-300">{item.label}</p>
<input
defaultValue={item.secret}
className="h-no-capture text-md min-w-16 no-scrollbar::-webkit-scrollbar peer z-10 w-full rounded-md bg-bunker-800 px-2 py-1.5 font-mono text-gray-400 caret-white outline-none duration-200 no-scrollbar focus:ring-2 focus:ring-primary/50 "
readOnly
/>
</div>
))}
</div>
</ModalContent>
</Modal>
);
};
export default CompareSecretsModal;
+44 -16
View File
@@ -7,9 +7,12 @@ import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import SecretVersionList from '@app/ee/components/SecretVersionList'; import SecretVersionList from '@app/ee/components/SecretVersionList';
import { WorkspaceEnv } from '~/pages/dashboard/[id]';
import Button from '../basic/buttons/Button'; import Button from '../basic/buttons/Button';
import Toggle from '../basic/Toggle'; import Toggle from '../basic/Toggle';
import CommentField from './CommentField'; import CommentField from './CommentField';
import CompareSecretsModal from './CompareSecretsModal';
import DashboardInputField from './DashboardInputField'; import DashboardInputField from './DashboardInputField';
import { DeleteActionButton } from './DeleteActionButton'; import { DeleteActionButton } from './DeleteActionButton';
import GenerateSecretMenu from './GenerateSecretMenu'; import GenerateSecretMenu from './GenerateSecretMenu';
@@ -40,6 +43,9 @@ interface SideBarProps {
sharedToHide: string[]; sharedToHide: string[];
setSharedToHide: (values: string[]) => void; setSharedToHide: (values: string[]) => void;
deleteRow: (props: DeleteRowFunctionProps) => void; deleteRow: (props: DeleteRowFunctionProps) => void;
workspaceEnvs: WorkspaceEnv[];
selectedEnv: WorkspaceEnv;
workspaceId: string;
} }
/** /**
@@ -63,11 +69,15 @@ const SideBar = ({
modifyComment, modifyComment,
buttonReady, buttonReady,
savePush, savePush,
deleteRow deleteRow,
workspaceEnvs,
selectedEnv,
workspaceId
}: SideBarProps) => { }: SideBarProps) => {
// eslint-disable-next-line @typescript-eslint/no-unused-vars // eslint-disable-next-line @typescript-eslint/no-unused-vars
const [isLoading, setIsLoading] = useState(false); const [isLoading, setIsLoading] = useState(false);
const [overrideEnabled, setOverrideEnabled] = useState(data[0].valueOverride !== undefined); const [overrideEnabled, setOverrideEnabled] = useState(data[0]?.valueOverride !== undefined);
const [compareModal, setCompareModal] = useState(false);
const { t } = useTranslation(); const { t } = useTranslation();
return ( return (
@@ -171,20 +181,38 @@ const SideBar = ({
/> />
</div> </div>
)} )}
<div className="flex justify-start max-w-sm mt-4 px-4 mt-full mb-[4.7rem]"> <div className="mt-full mt-4 mb-[4.7rem] flex max-w-sm flex-col justify-start space-y-2 px-4">
<Button <div>
text={String(t('common:save-changes'))} <Button
onButtonPressed={savePush} text="Compare secret across environments"
color="primary" color="mineshaft"
size="md" size="md"
active={buttonReady} onButtonPressed={() => setCompareModal(true)}
textDisabled="Saved" />
/> <CompareSecretsModal
<DeleteActionButton compareModal={compareModal}
onSubmit={() => setCompareModal={setCompareModal}
deleteRow({ ids: data.map((secret) => secret.id), secretName: data[0]?.key }) currentSecret={{ key: data[0]?.key, value: data[0]?.value }}
} workspaceEnvs={workspaceEnvs}
/> selectedEnv={selectedEnv}
workspaceId={workspaceId}
/>
</div>
<div className="flex">
<Button
text={String(t('common:save-changes'))}
onButtonPressed={savePush}
color="primary"
size="md"
active={buttonReady}
textDisabled="Saved"
/>
<DeleteActionButton
onSubmit={() =>
deleteRow({ ids: data.map((secret) => secret.id), secretName: data[0]?.key })
}
/>
</div>
</div> </div>
</div> </div>
); );