refactor: Make DeleteButton.tsx generic

This commit is contained in:
Myzel394 2023-02-14 20:18:04 +01:00
parent d786199111
commit 00b983aed2
6 changed files with 55 additions and 22 deletions

View File

@ -16,7 +16,8 @@
"loading": "Loading...", "loading": "Loading...",
"actionNotUndoable": "This action cannot be undone!", "actionNotUndoable": "This action cannot be undone!",
"copyError": "Copying to clipboard did not work. Please copy the text manually.", "copyError": "Copying to clipboard did not work. Please copy the text manually.",
"experimentalFeature": "This is an experimental feature." "experimentalFeature": "This is an experimental feature.",
"deletedSuccessfully": "Deleted successfully!"
}, },
"routes": { "routes": {

View File

@ -82,6 +82,7 @@ const router = createBrowserRouter([
}, },
{ {
path: "/aliases/:id", path: "/aliases/:id",
loader: getServerSettings,
element: <AliasDetailRoute />, element: <AliasDetailRoute />,
}, },
{ {

View File

@ -15,24 +15,35 @@ import {
} from "@mui/material" } from "@mui/material"
import {useMutation} from "@tanstack/react-query" import {useMutation} from "@tanstack/react-query"
import {deleteReport} from "~/apis"
import {useErrorSuccessSnacks} from "~/hooks" import {useErrorSuccessSnacks} from "~/hooks"
import {SimpleDetailResponse} from "~/server-types"
export interface DeleteButtonProps { export interface DeleteAPIButtonProps {
id: string onDelete: () => Promise<any>
label: string
continueLabel?: string
description?: string
successMessage?: string
navigateTo?: string
} }
export default function ReportDetailRoute({id}: DeleteButtonProps): ReactElement { export default function DeleteAPIButton({
onDelete,
successMessage,
label,
continueLabel,
description,
navigateTo = "/aliases",
}: DeleteAPIButtonProps): ReactElement {
const {t} = useTranslation() const {t} = useTranslation()
const {showError, showSuccess} = useErrorSuccessSnacks() const {showError, showSuccess} = useErrorSuccessSnacks()
const navigate = useNavigate() const navigate = useNavigate()
const {mutate} = useMutation<SimpleDetailResponse, AxiosError, void>(() => deleteReport(id), { const {mutate} = useMutation<void, AxiosError, void>(onDelete, {
onError: showError, onError: showError,
onSuccess: () => { onSuccess: () => {
showSuccess(t("relations.report.mutations.success.reportDeleted")) showSuccess(successMessage || t("general.deletedSuccessfully"))
navigate("/reports") navigate(navigateTo)
}, },
}) })
@ -47,14 +58,12 @@ export default function ReportDetailRoute({id}: DeleteButtonProps): ReactElement
startIcon={<MdDelete />} startIcon={<MdDelete />}
onClick={() => setShowDeleteDialog(true)} onClick={() => setShowDeleteDialog(true)}
> >
{t("routes.ReportDetailRoute.actions.delete.label")} {label}
</Button> </Button>
<Dialog open={showDeleteDialog} onClose={() => setShowDeleteDialog(false)}> <Dialog open={showDeleteDialog} onClose={() => setShowDeleteDialog(false)}>
<DialogTitle>{t("routes.ReportDetailRoute.actions.delete.label")}</DialogTitle> <DialogTitle>{label}</DialogTitle>
<DialogContent> <DialogContent>
<DialogContentText> {description && <DialogContentText>{description}</DialogContentText>}
{t("routes.ReportDetailRoute.actions.delete.description")}
</DialogContentText>
<DialogContentText color="error"> <DialogContentText color="error">
{t("general.actionNotUndoable")} {t("general.actionNotUndoable")}
</DialogContentText> </DialogContentText>
@ -69,7 +78,7 @@ export default function ReportDetailRoute({id}: DeleteButtonProps): ReactElement
color="error" color="error"
onClick={() => mutate()} onClick={() => mutate()}
> >
{t("routes.ReportDetailRoute.actions.delete.continueAction")} {continueLabel}
</Button> </Button>
</DialogActions> </DialogActions>
</Dialog> </Dialog>

View File

@ -45,6 +45,8 @@ export {default as LoadingData} from "./LoadingData"
export * from "./ExternalLinkIndication" export * from "./ExternalLinkIndication"
export {default as ExternalLinkIndication} from "./ExternalLinkIndication" export {default as ExternalLinkIndication} from "./ExternalLinkIndication"
export {default as ExtensionSignalHandler} from "./ExtensionalSignalHandler" export {default as ExtensionSignalHandler} from "./ExtensionalSignalHandler"
export * from "./DeleteAPIButton"
export {default as DeleteButton} from "./DeleteAPIButton"
export * from "./StringPoolField" export * from "./StringPoolField"
export * as SimplePageBuilder from "./simple-page-builder" export * as SimplePageBuilder from "./simple-page-builder"

View File

@ -1,5 +1,5 @@
import {ReactElement, useContext} from "react" import {ReactElement, useContext} from "react"
import {useParams} from "react-router-dom" import {useLoaderData, useParams} from "react-router-dom"
import {AxiosError} from "axios" import {AxiosError} from "axios"
import {useTranslation} from "react-i18next" import {useTranslation} from "react-i18next"
@ -7,7 +7,7 @@ import {useQuery} from "@tanstack/react-query"
import {Grid} from "@mui/material" import {Grid} from "@mui/material"
import {getAlias} from "~/apis" import {getAlias} from "~/apis"
import {Alias, DecryptedAlias} from "~/server-types" import {Alias, DecryptedAlias, ServerSettings} from "~/server-types"
import { import {
AliasTypeIndicator, AliasTypeIndicator,
AuthContext, AuthContext,
@ -25,6 +25,7 @@ import decryptAliasNotes from "~/apis/helpers/decrypt-alias-notes"
export default function AliasDetailRoute(): ReactElement { export default function AliasDetailRoute(): ReactElement {
const {t} = useTranslation() const {t} = useTranslation()
const serverSettings = useLoaderData() as ServerSettings
const {id: aliasID} = useParams() const {id: aliasID} = useParams()
const {_decryptUsingMasterPassword, encryptionStatus} = useContext(AuthContext) const {_decryptUsingMasterPassword, encryptionStatus} = useContext(AuthContext)
const queryKey = ["get_alias", aliasID, encryptionStatus] const queryKey = ["get_alias", aliasID, encryptionStatus]
@ -43,7 +44,10 @@ export default function AliasDetailRoute(): ReactElement {
}) })
return ( return (
<SimplePage title={t("routes.AliasDetailRoute.title")}> <SimplePage
title={t("routes.AliasDetailRoute.title")}
actions={query.data && <DeleteButton id={query.data.id} />}
>
<QueryResult<Alias | DecryptedAlias> query={query}> <QueryResult<Alias | DecryptedAlias> query={query}>
{alias => ( {alias => (
<SimplePageBuilder.MultipleSections> <SimplePageBuilder.MultipleSections>

View File

@ -7,10 +7,15 @@ import {useQuery} from "@tanstack/react-query"
import {List} from "@mui/material" import {List} from "@mui/material"
import {DecryptedReportContent, Report} from "~/server-types" import {DecryptedReportContent, Report} from "~/server-types"
import {getReport} from "~/apis" import {deleteReport, getReport} from "~/apis"
import {DecryptReport, QueryResult, SimpleOverlayInformation, SimplePageBuilder} from "~/components" import {
DecryptReport,
DeleteButton,
QueryResult,
SimpleOverlayInformation,
SimplePageBuilder,
} from "~/components"
import {WithEncryptionRequired} from "~/hocs" import {WithEncryptionRequired} from "~/hocs"
import DeleteButton from "~/route-widgets/ReportDetailRoute/DeleteButton"
import ExpandedUrlsListItem from "~/route-widgets/ReportDetailRoute/ExpandedUrlsListItem" import ExpandedUrlsListItem from "~/route-widgets/ReportDetailRoute/ExpandedUrlsListItem"
import ProxiedImagesListItem from "~/route-widgets/ReportDetailRoute/ProxiedImagesListItem" import ProxiedImagesListItem from "~/route-widgets/ReportDetailRoute/ProxiedImagesListItem"
import SinglePixelImageTrackersListItem from "~/route-widgets/ReportDetailRoute/SinglePixelImageTrackersListItem" import SinglePixelImageTrackersListItem from "~/route-widgets/ReportDetailRoute/SinglePixelImageTrackersListItem"
@ -26,7 +31,18 @@ function ReportDetailRoute(): ReactElement {
return ( return (
<SimplePageBuilder.Page <SimplePageBuilder.Page
title="Report Details" title="Report Details"
actions={query.data && <DeleteButton id={query.data.id} />} actions={
query.data && (
<DeleteButton
onDelete={() => deleteReport(params.id!)}
label={t("routes.ReportDetailRoute.actions.delete.label")}
description={t("routes.ReportDetailRoute.actions.delete.description")}
continueLabel={t("routes.ReportDetailRoute.actions.delete.continueAction")}
navigateTo={"/reports"}
successMessage={t("relations.report.mutations.success.reportDeleted")}
/>
)
}
> >
<QueryResult<Report> query={query}> <QueryResult<Report> query={query}>
{encryptedReport => ( {encryptedReport => (