Seth
Update
f6e574f
import React, { useState } from "react";
export default function App() {
const [file, setFile] = useState(null);
const [loading, setLoading] = useState(false);
const [result, setResult] = useState(null);
const [error, setError] = useState(null);
const handleFileChange = (e) => {
const selectedFile = e.target.files[0];
if (selectedFile) {
if (selectedFile.type !== "application/pdf") {
setError("Please select a PDF file");
setFile(null);
return;
}
setFile(selectedFile);
setError(null);
setResult(null);
}
};
const handleClassify = async () => {
if (!file) {
setError("Please select a PDF file first");
return;
}
setLoading(true);
setError(null);
setResult(null);
const formData = new FormData();
formData.append("file", file);
try {
const response = await fetch("/api/classify", {
method: "POST",
body: formData,
});
if (!response.ok) {
const errorData = await response.json();
throw new Error(errorData.detail || "Classification failed");
}
const data = await response.json();
setResult(data);
} catch (err) {
setError(err.message || "An error occurred during classification");
} finally {
setLoading(false);
}
};
const handleReset = () => {
setFile(null);
setResult(null);
setError(null);
// Reset file input
const fileInput = document.getElementById("pdf-upload");
if (fileInput) fileInput.value = "";
};
return (
<div
style={{
fontFamily: "system-ui, -apple-system, sans-serif",
maxWidth: "800px",
margin: "0 auto",
padding: "24px",
lineHeight: 1.6,
}}
>
<div style={{ textAlign: "center", marginBottom: "32px" }}>
<h1 style={{ margin: "0 0 8px 0", color: "#1a1a1a" }}>
📄 Document Classifier
</h1>
<p style={{ color: "#666", margin: "0" }}>
Upload a PDF file to classify its document type using BERT-tiny
</p>
</div>
<div
style={{
border: "2px dashed #ddd",
borderRadius: "12px",
padding: "32px",
textAlign: "center",
backgroundColor: "#fafafa",
marginBottom: "24px",
}}
>
<input
id="pdf-upload"
type="file"
accept=".pdf"
onChange={handleFileChange}
style={{ display: "none" }}
/>
<label
htmlFor="pdf-upload"
style={{
display: "inline-block",
padding: "12px 24px",
backgroundColor: "#4f46e5",
color: "white",
borderRadius: "8px",
cursor: "pointer",
fontSize: "16px",
fontWeight: "500",
marginBottom: "16px",
transition: "background-color 0.2s",
}}
onMouseOver={(e) => (e.target.style.backgroundColor = "#4338ca")}
onMouseOut={(e) => (e.target.style.backgroundColor = "#4f46e5")}
>
{file ? "Change PDF File" : "Select PDF File"}
</label>
{file && (
<div style={{ marginTop: "16px" }}>
<p style={{ margin: "8px 0", color: "#333" }}>
<strong>Selected:</strong> {file.name}
</p>
<p style={{ margin: "4px 0", color: "#666", fontSize: "14px" }}>
Size: {(file.size / 1024).toFixed(2)} KB
</p>
</div>
)}
<div style={{ marginTop: "24px" }}>
<button
onClick={handleClassify}
disabled={!file || loading}
style={{
padding: "12px 32px",
fontSize: "16px",
fontWeight: "600",
backgroundColor: file && !loading ? "#10b981" : "#9ca3af",
color: "white",
border: "none",
borderRadius: "8px",
cursor: file && !loading ? "pointer" : "not-allowed",
transition: "background-color 0.2s",
}}
onMouseOver={(e) => {
if (file && !loading) {
e.target.style.backgroundColor = "#059669";
}
}}
onMouseOut={(e) => {
if (file && !loading) {
e.target.style.backgroundColor = "#10b981";
}
}}
>
{loading ? "Classifying..." : "Classify Document"}
</button>
{file && (
<button
onClick={handleReset}
disabled={loading}
style={{
padding: "12px 24px",
fontSize: "16px",
fontWeight: "500",
backgroundColor: "transparent",
color: "#666",
border: "1px solid #ddd",
borderRadius: "8px",
cursor: loading ? "not-allowed" : "pointer",
marginLeft: "12px",
}}
>
Reset
</button>
)}
</div>
</div>
{error && (
<div
style={{
padding: "16px",
backgroundColor: "#fee2e2",
border: "1px solid #fecaca",
borderRadius: "8px",
color: "#991b1b",
marginBottom: "24px",
}}
>
<strong>Error:</strong> {error}
</div>
)}
{result && (
<div
style={{
padding: "24px",
backgroundColor: "#f0fdf4",
border: "2px solid #86efac",
borderRadius: "12px",
marginBottom: "24px",
}}
>
<h2 style={{ margin: "0 0 16px 0", color: "#166534" }}>
Classification Result
</h2>
<div
style={{
backgroundColor: "white",
padding: "20px",
borderRadius: "8px",
marginBottom: "16px",
}}
>
<div style={{ marginBottom: "12px" }}>
<span style={{ color: "#666", fontSize: "14px" }}>
Document Type:
</span>
<div
style={{
fontSize: "24px",
fontWeight: "700",
color: "#10b981",
marginTop: "4px",
textTransform: "capitalize",
}}
>
{result.classification.document_type}
</div>
</div>
<div style={{ marginBottom: "12px" }}>
<span style={{ color: "#666", fontSize: "14px" }}>
Confidence:
</span>
<div
style={{
fontSize: "20px",
fontWeight: "600",
color: "#059669",
marginTop: "4px",
}}
>
{(result.classification.confidence * 100).toFixed(1)}%
</div>
</div>
<div style={{ marginTop: "16px", paddingTop: "16px", borderTop: "1px solid #e5e7eb" }}>
<span style={{ color: "#666", fontSize: "14px" }}>
File: {result.filename}
</span>
<br />
<span style={{ color: "#666", fontSize: "14px" }}>
Text Length: {result.text_length.toLocaleString()} characters
</span>
</div>
</div>
{result.classification.all_scores && (
<div>
<h3 style={{ margin: "0 0 12px 0", fontSize: "16px", color: "#166534" }}>
Top 5 Classifications:
</h3>
<div style={{ backgroundColor: "white", padding: "16px", borderRadius: "8px" }}>
{Object.entries(result.classification.all_scores).map(
([type, score]) => (
<div
key={type}
style={{
display: "flex",
justifyContent: "space-between",
alignItems: "center",
padding: "8px 0",
borderBottom: "1px solid #f3f4f6",
}}
>
<span style={{ textTransform: "capitalize", color: "#374151" }}>
{type}
</span>
<span
style={{
fontWeight: "600",
color: type === result.classification.document_type ? "#10b981" : "#6b7280",
}}
>
{(score * 100).toFixed(1)}%
</span>
</div>
)
)}
</div>
</div>
)}
</div>
)}
{loading && (
<div style={{ textAlign: "center", padding: "24px" }}>
<div
style={{
display: "inline-block",
width: "40px",
height: "40px",
border: "4px solid #e5e7eb",
borderTop: "4px solid #4f46e5",
borderRadius: "50%",
animation: "spin 1s linear infinite",
}}
/>
<p style={{ marginTop: "16px", color: "#666" }}>
Processing your document...
</p>
</div>
)}
</div>
);
}