mirror of
https://github.com/itplr-kosit/validator.git
synced 2026-05-26 01:05:38 +00:00
Resolve https://projekte.kosit.org/kosit/validator/-/issues/97 "Replace docsify from UI"
This commit is contained in:
parent
a10cc14d06
commit
219aeaa1b7
100 changed files with 27369 additions and 1072 deletions
14
server/ui/src/components/Upload/Upload.module.css
Normal file
14
server/ui/src/components/Upload/Upload.module.css
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
.buttonGroup {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
margin: 1rem 0;
|
||||
}
|
||||
|
||||
.resultDisplay {
|
||||
margin: 1em 0;
|
||||
}
|
||||
|
||||
.withError {
|
||||
border: 0.2rem solid var(--text-error);
|
||||
border-radius: var(--border-radius-small);
|
||||
}
|
||||
115
server/ui/src/components/Upload/Upload.tsx
Normal file
115
server/ui/src/components/Upload/Upload.tsx
Normal file
|
|
@ -0,0 +1,115 @@
|
|||
import type { FormEventHandler } from "react";
|
||||
import React, { useCallback, useState } from "react";
|
||||
import clsx from "clsx";
|
||||
import Dropzone from "../Dropzone";
|
||||
import Codeblock from "../Codeblock";
|
||||
import ErrorDisplay from "../ErrorDisplay";
|
||||
import useRequest, { RequestStatus } from "../util/useRequest";
|
||||
import Button from "../Button";
|
||||
import styles from "./Upload.module.css";
|
||||
|
||||
const ENDPOINT = "/";
|
||||
|
||||
const ACCEPT = {
|
||||
"text/xml": [".xml", ".XML"],
|
||||
"application/xml": [".xml", ".XML"],
|
||||
};
|
||||
|
||||
function createFileName(selectedFileName: string | undefined) {
|
||||
return selectedFileName
|
||||
? `${selectedFileName.replace(/\.xml$/i, "")}-report.xml`
|
||||
: "report.xml";
|
||||
}
|
||||
|
||||
function Upload(): JSX.Element {
|
||||
const [selectedFile, setSelectedFile] = useState<File | null>(null);
|
||||
const [rejected, setRejected] = useState<File[]>([]);
|
||||
const { data, error, request, status } = useRequest();
|
||||
|
||||
const handleDrop = useCallback(
|
||||
(acceptedFiles: File[], rejectedFiles: File[]) => {
|
||||
if (acceptedFiles.length) {
|
||||
setSelectedFile(acceptedFiles[0]);
|
||||
setRejected([]);
|
||||
} else {
|
||||
setRejected(rejectedFiles);
|
||||
}
|
||||
},
|
||||
[],
|
||||
);
|
||||
|
||||
const handleSubmit: FormEventHandler<HTMLFormElement> = (e) => {
|
||||
e.preventDefault();
|
||||
if (!selectedFile) return;
|
||||
request(ENDPOINT, {
|
||||
method: "POST",
|
||||
headers: { "Content-Type": "application/xml" },
|
||||
body: selectedFile,
|
||||
redirect: "follow",
|
||||
});
|
||||
};
|
||||
|
||||
const meaningfulErrorResponse = !!error && [406, 422].includes(error.code);
|
||||
|
||||
return (
|
||||
<>
|
||||
<form onSubmit={handleSubmit}>
|
||||
{status === RequestStatus.Failure && error && !meaningfulErrorResponse && (
|
||||
<ErrorDisplay title="An error occurred while validating the file">
|
||||
<Codeblock enableCopy>{error.message}</Codeblock>
|
||||
</ErrorDisplay>
|
||||
)}
|
||||
{rejected.length > 1 && (
|
||||
<ErrorDisplay title="Please select a single file only" />
|
||||
)}
|
||||
{rejected.length === 1 && (
|
||||
<ErrorDisplay title="Only XML files are supported">
|
||||
<Codeblock>{`Invalid file found: ${rejected[0].name}`}</Codeblock>
|
||||
</ErrorDisplay>
|
||||
)}
|
||||
<Dropzone
|
||||
onDrop={handleDrop}
|
||||
accept={ACCEPT}
|
||||
multiple={false}
|
||||
hasSelectedFiles={!!selectedFile}
|
||||
>
|
||||
{selectedFile ? (
|
||||
selectedFile.name
|
||||
) : (
|
||||
<>Drag & drop files here or click to select a file</>
|
||||
)}
|
||||
</Dropzone>
|
||||
<div className={styles.buttonGroup}>
|
||||
<Button
|
||||
type="submit"
|
||||
disabled={!selectedFile}
|
||||
loading={status === RequestStatus.Loading}
|
||||
>
|
||||
Validate
|
||||
</Button>
|
||||
</div>
|
||||
</form>
|
||||
{((data && status === RequestStatus.Success) ||
|
||||
meaningfulErrorResponse) && (
|
||||
<div
|
||||
className={clsx(
|
||||
styles.resultDisplay,
|
||||
meaningfulErrorResponse && styles.withError,
|
||||
)}
|
||||
>
|
||||
<Codeblock
|
||||
download={{
|
||||
fileName: createFileName(selectedFile?.name),
|
||||
mime: "application/xml",
|
||||
}}
|
||||
enableCopy
|
||||
>
|
||||
{data || error?.message || ""}
|
||||
</Codeblock>
|
||||
</div>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
export default Upload;
|
||||
3
server/ui/src/components/Upload/index.ts
Normal file
3
server/ui/src/components/Upload/index.ts
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
import Upload from "./Upload";
|
||||
|
||||
export default Upload;
|
||||
Loading…
Add table
Add a link
Reference in a new issue