feat: Create user page (#1197)

* Add button and route

* Hook up api

* Lint

* Add basic form

* Get users on page mount

* Make cancel work

* Creating -> idle bc users page refetches

* Import as TypesGen

* Handle api errors

* Lint

* Add handler

* Add FormFooter

* Add FullPageForm

* Lint

* Better form, error, stories

bug in formErrors story

* Make detail optional

* Use Language

* Remove detail prop

* Add back autoFocus

* Remove displayError, use displaySuccess

* Lint, export Language

* Tests - wip

* Fix cancel tests

* Switch back to mock

* Add navigate to xservice

Doesn't work in test

* Move error type predicate to xservice

* Lint

* Switch to using creation mode in XState

still problems in tests

* Lint

* Lint

* Lint

* Revert "Switch to using creation mode in XState"

This reverts commit cf8442fa4b.

* Give XService a navigate action

* Add missing validation messages

* Fix XState warning

* Fix tests

IRL is broken bc I need to send org id

* Pretend user has org id and make it work

* Format

* Lint

* Switch to org ids array

* Skip lines between tests

Co-authored-by: G r e y <grey@coder.com>

* Punctuate notification messages

Co-authored-by: G r e y <grey@coder.com>
This commit is contained in:
Presley Pizzo
2022-04-28 16:32:23 -04:00
committed by GitHub
parent 4efde58726
commit c16f105727
17 changed files with 412 additions and 23 deletions

View File

@ -0,0 +1,92 @@
import FormHelperText from "@material-ui/core/FormHelperText"
import TextField from "@material-ui/core/TextField"
import { FormikContextType, FormikErrors, useFormik } from "formik"
import React from "react"
import * as Yup from "yup"
import { CreateUserRequest } from "../../api/types"
import { getFormHelpers, onChangeTrimmed } from "../../util/formUtils"
import { FormFooter } from "../FormFooter/FormFooter"
import { FullPageForm } from "../FullPageForm/FullPageForm"
export const Language = {
emailLabel: "Email",
passwordLabel: "Password",
usernameLabel: "Username",
emailInvalid: "Please enter a valid email address.",
emailRequired: "Please enter an email address.",
passwordRequired: "Please enter a password.",
usernameRequired: "Please enter a username.",
createUser: "Create",
cancel: "Cancel",
}
export interface CreateUserFormProps {
onSubmit: (user: CreateUserRequest) => void
onCancel: () => void
formErrors?: FormikErrors<CreateUserRequest>
isLoading: boolean
error?: string
myOrgId: string
}
const validationSchema = Yup.object({
email: Yup.string().trim().email(Language.emailInvalid).required(Language.emailRequired),
password: Yup.string().required(Language.passwordRequired),
username: Yup.string().required(Language.usernameRequired),
})
export const CreateUserForm: React.FC<CreateUserFormProps> = ({
onSubmit,
onCancel,
formErrors,
isLoading,
error,
myOrgId,
}) => {
const form: FormikContextType<CreateUserRequest> = useFormik<CreateUserRequest>({
initialValues: {
email: "",
password: "",
username: "",
organization_id: myOrgId,
},
validationSchema,
onSubmit,
})
const getFieldHelpers = getFormHelpers<CreateUserRequest>(form, formErrors)
return (
<FullPageForm title="Create user" onCancel={onCancel}>
<form onSubmit={form.handleSubmit}>
<TextField
{...getFieldHelpers("username")}
onChange={onChangeTrimmed(form)}
autoComplete="username"
autoFocus
fullWidth
label={Language.usernameLabel}
variant="outlined"
/>
<TextField
{...getFieldHelpers("email")}
onChange={onChangeTrimmed(form)}
autoComplete="email"
fullWidth
label={Language.emailLabel}
variant="outlined"
/>
<TextField
{...getFieldHelpers("password")}
autoComplete="current-password"
fullWidth
id="password"
label={Language.passwordLabel}
type="password"
variant="outlined"
/>
{error && <FormHelperText error>{error}</FormHelperText>}
<FormFooter onCancel={onCancel} isLoading={isLoading} />
</form>
</FullPageForm>
)
}