I am a newbie to web-dev and learning React. I have used ZOD for form implementation. My IDE is not showing any errors but when I click on submit button, screen doesn’t gets re-render. It would be nice if someone can help me out. I know its a small issue, but I have been scratching my head for over a day.
APP.TSX
import { useEffect, useState } from "react";
import StudentGradingEvaluationForm, {
StudentFormData,
} from "./Components/StudentGradingEvaluationForm";
import GPACalculator from "./Components/GPACalculator";
import "./Components/Courses";
const App = () => {
const [formData, setFormData] = useState<StudentFormData | null>(null);
const [isFormSubmitted, setIsFormSubmitted] = useState(false);
const handleFormSubmitted = (data: StudentFormData) => {
if (data) {
setFormData(data);
setIsFormSubmitted(true);
}
};
const resetForm = () => {
setFormData(null);
setIsFormSubmitted(false);
};
return (
<>
<div style={{ textAlign: "center" }}>
<h1>GPA Calculator for Individual Student</h1>
</div>
<div>
{!isFormSubmitted && (
<StudentGradingEvaluationForm onSubmit={handleFormSubmitted} />
)}
{isFormSubmitted && !formData && (
<p className="text-danger">Enter correct credentials</p>
)}
</div>
{formData && (
<button className="btn btn-outline-danger" onClick={resetForm}>
Reset Form
</button>
)}
{formData && formData.courses && (
<GPACalculator
subject={formData.courses}
number={formData.number}
name={formData.name}
/>
)}
</>
);
};
export default App;
StudentGradingEvaluationForm.tsx
import { z } from "zod";
import { useForm } from "react-hook-form";
import { zodResolver } from "@hookform/resolvers/zod";
import courses from "./Courses";
const schema = z.object({
name: z
.string()
.min(3, { message: "Description should be atleast 3 characters." }),
number: z.number().min(0).max(100),
courses: z.enum(courses, {
errorMap: () => ({ message: "Course is required." }),
}),
});
export type StudentFormData = z.infer<typeof schema>;
interface Props {
onSubmit: (data: StudentFormData) => void;
}
const StudentGradingEvaluationForm = ({ onSubmit }: Props) => {
const { register, handleSubmit } = useForm<StudentFormData>({
resolver: zodResolver(schema),
});
return (
<form
onSubmit={handleSubmit((data) => {
onSubmit(data);
console.log(onSubmit);
})}
>
<div className="mb-3">
<label htmlFor="studentName" className="form-label">
Name of Student
</label>
<input
id="studentName"
type="text"
className="form-control"
{...register("name")}
/>
</div>
<div className="mb-3">
<label htmlFor="courseName" className="form-label">
Name of Course
</label>
<div>
<select
id="courseName"
className="select-control"
{...register("courses")}
>
<option value=""></option>
{courses.map((course) => (
<option key={course} value={course}>
{course}
</option>
))}
</select>
</div>
</div>
<div className="mb-3">
<label htmlFor="number" className="form-label">
Enter Number
</label>
<input
id="number"
type="number"
className="form-control"
{...register("number")}
/>
</div>
<button type="submit" className="btn btn-primary">
Submit
</button>
</form>
);
};
export default StudentGradingEvaluationForm;
Courses.ts
const courses = [
"Mechanics of Materials - I",
"Fluid Dynamics - I",
"Ordinary Differential Equations",
"Thermodynamics - II",
"Basic Electrical and Electronics Engineering",
] as const;
export default courses;
GPACalculator.tsx
interface Props {
subject: string;
name: string;
number: number;
}
const GPACalculator = ({ subject, number, name }: Props) => {
const calculateGpa = () => {
if (number < 100 && number >= 80) return "A";
else if (number < 80 && number >= 65) return "B";
else if (number < 65 && number >= 55) return "C";
else if (number < 55 && number >= 40) return "D";
else return "FAIL";
};
return (
<div>
<h2>GPA Calculator Result for {name}</h2>
<p>Subject: {subject}</p>
<p>Number: {number}</p>
<p>GPA: {calculateGpa()}</p>
</div>
);
};
export default GPACalculator;
I have used following dependencies:
npm create [email protected] npm i bootstrap npm i zod npm i [email protected] npm i @hookform/[email protected]
VS Code isn’t showing any error. Soon as I click on submit button, nothing happens. I believe my code is simple and self-explanatory. Looking forward for help.
2
Answers
So the issue is, there is no error on your code. Your code is working fine. But you have form validation error for zod resolver. And as you are not showing any form error, you can not see the problem here.
Attaching the error you were getting with your current code –
How to fix:
just register the number input like I have shown here.
Another thing:
update these lines in your code at the top of StudentGradingEvaluationForm component to see the error states log.
Please upvote if this helps!
Let me know if you have any questions.
By default, react-hook-form treats input values as strings
I updated Schema z.number() to z.coerce.number()
I add message for better understanding