mirror of
https://github.com/coder/coder.git
synced 2026-09-24 15:04:27 +08:00
Handle api errors
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
import Button from "@material-ui/core/Button"
|
||||
import TextField from "@material-ui/core/TextField"
|
||||
import { FormikContextType, useFormik } from "formik"
|
||||
import { FormikContextType, FormikErrors, useFormik } from "formik"
|
||||
import React from "react"
|
||||
import * as Yup from "yup"
|
||||
import { CreateUserRequest } from "../../api/typesGenerated"
|
||||
@@ -22,6 +22,7 @@ const Language = {
|
||||
export interface CreateUserFormProps {
|
||||
onSubmit: (user: CreateUserRequest) => void
|
||||
onCancel: () => void
|
||||
formErrors?: FormikErrors<CreateUserRequest>
|
||||
}
|
||||
|
||||
const validationSchema = Yup.object({
|
||||
@@ -30,7 +31,7 @@ const validationSchema = Yup.object({
|
||||
username: Yup.string().required(),
|
||||
})
|
||||
|
||||
export const CreateUserForm: React.FC<CreateUserFormProps> = ({ onSubmit, onCancel }) => {
|
||||
export const CreateUserForm: React.FC<CreateUserFormProps> = ({ onSubmit, onCancel, formErrors }) => {
|
||||
const form: FormikContextType<CreateUserRequest> = useFormik<CreateUserRequest>({
|
||||
initialValues: {
|
||||
email: "",
|
||||
@@ -40,11 +41,12 @@ export const CreateUserForm: React.FC<CreateUserFormProps> = ({ onSubmit, onCanc
|
||||
validationSchema,
|
||||
onSubmit,
|
||||
})
|
||||
const getFieldHelpers = getFormHelpers<CreateUserRequest>(form, formErrors)
|
||||
|
||||
return (
|
||||
<form onSubmit={form.handleSubmit}>
|
||||
<TextField
|
||||
{...getFormHelpers<CreateUserRequest>(form, "username")}
|
||||
{...getFieldHelpers("username")}
|
||||
onChange={onChangeTrimmed(form)}
|
||||
autoFocus
|
||||
autoComplete="username"
|
||||
@@ -53,7 +55,7 @@ export const CreateUserForm: React.FC<CreateUserFormProps> = ({ onSubmit, onCanc
|
||||
variant="outlined"
|
||||
/>
|
||||
<TextField
|
||||
{...getFormHelpers<CreateUserRequest>(form, "email")}
|
||||
{...getFieldHelpers("email")}
|
||||
onChange={onChangeTrimmed(form)}
|
||||
autoFocus
|
||||
autoComplete="email"
|
||||
@@ -62,7 +64,7 @@ export const CreateUserForm: React.FC<CreateUserFormProps> = ({ onSubmit, onCanc
|
||||
variant="outlined"
|
||||
/>
|
||||
<TextField
|
||||
{...getFormHelpers<CreateUserRequest>(form, "password")}
|
||||
{...getFieldHelpers("password")}
|
||||
autoComplete="current-password"
|
||||
fullWidth
|
||||
id="password"
|
||||
|
||||
@@ -1,14 +1,24 @@
|
||||
import { useActor } from "@xstate/react"
|
||||
import React, { useContext } from "react"
|
||||
import { useNavigate } from "react-router"
|
||||
import { isApiError, mapApiErrorToFieldErrors } from "../../../api/errors"
|
||||
import { CreateUserRequest } from "../../../api/typesGenerated"
|
||||
import { CreateUserForm } from "../../../components/CreateUserForm/CreateUserForm"
|
||||
import { XServiceContext } from "../../../xServices/StateContext"
|
||||
|
||||
export const CreateUserPage = () => {
|
||||
const xServices = useContext(XServiceContext)
|
||||
const [_, usersSend] = useActor(xServices.usersXService)
|
||||
const [usersState, usersSend] = useActor(xServices.usersXService)
|
||||
const { createUserError } = usersState.context
|
||||
const formErrors =
|
||||
createUserError && isApiError(createUserError) ? mapApiErrorToFieldErrors(createUserError.response.data) : undefined
|
||||
const navigate = useNavigate()
|
||||
|
||||
return <CreateUserForm onSubmit={(user: CreateUserRequest) => usersSend({ type: "CREATE", user })} onCancel={() => navigate("/users")} />
|
||||
return (
|
||||
<CreateUserForm
|
||||
formErrors={formErrors}
|
||||
onSubmit={(user: CreateUserRequest) => usersSend({ type: "CREATE", user })}
|
||||
onCancel={() => navigate("/users")}
|
||||
/>
|
||||
)
|
||||
}
|
||||
|
||||
@@ -70,11 +70,11 @@ export const usersMachine = createMachine(
|
||||
id: "createUser",
|
||||
onDone: {
|
||||
target: "idle",
|
||||
actions: "displayCreateUserSuccess",
|
||||
actions: ["displayCreateUserSuccess", "clearCreateUserError"],
|
||||
},
|
||||
onError: {
|
||||
target: "idle",
|
||||
actions: "displayCreateUserError",
|
||||
actions: ["assignCreateUserError", "displayCreateUserError"],
|
||||
},
|
||||
},
|
||||
tags: "loading",
|
||||
@@ -103,7 +103,14 @@ export const usersMachine = createMachine(
|
||||
...context,
|
||||
getUsersError: undefined,
|
||||
})),
|
||||
displayCreateUserError: () => {
|
||||
assignCreateUserError: assign({
|
||||
createUserError: (_, event) => event.data
|
||||
}),
|
||||
clearCreateUserError: assign((context: UsersContext) => ({
|
||||
...context,
|
||||
createUserError: undefined
|
||||
})),
|
||||
displayCreateUserError: (_, event) => {
|
||||
displayError(Language.createUserError)
|
||||
},
|
||||
displayCreateUserSuccess: () => {
|
||||
|
||||
Reference in New Issue
Block a user