ui(admin): add 'externalId' field for users
This commit is contained in:
parent
9c92d51e28
commit
81ff03c2a3
4 changed files with 63 additions and 42 deletions
|
@ -2,6 +2,7 @@ import http from '@/api/http';
|
||||||
import { User, rawDataToUser } from '@/api/admin/users/getUsers';
|
import { User, rawDataToUser } from '@/api/admin/users/getUsers';
|
||||||
|
|
||||||
export interface Values {
|
export interface Values {
|
||||||
|
externalId: string;
|
||||||
username: string;
|
username: string;
|
||||||
email: string;
|
email: string;
|
||||||
password: string;
|
password: string;
|
||||||
|
|
|
@ -39,6 +39,7 @@ const UserAboutContainer = () => {
|
||||||
<UserForm
|
<UserForm
|
||||||
title={'Edit User'}
|
title={'Edit User'}
|
||||||
initialValues={{
|
initialValues={{
|
||||||
|
externalId: user.externalId,
|
||||||
username: user.username,
|
username: user.username,
|
||||||
email: user.email,
|
email: user.email,
|
||||||
adminRoleId: user.adminRoleId,
|
adminRoleId: user.adminRoleId,
|
||||||
|
@ -46,7 +47,8 @@ const UserAboutContainer = () => {
|
||||||
rootAdmin: user.rootAdmin,
|
rootAdmin: user.rootAdmin,
|
||||||
}}
|
}}
|
||||||
onSubmit={submit}
|
onSubmit={submit}
|
||||||
role={user?.relationships.role || null}
|
uuid={user.uuid}
|
||||||
|
role={user.relationships.role || null}
|
||||||
>
|
>
|
||||||
<div css={tw`flex`}>
|
<div css={tw`flex`}>
|
||||||
<UserDeleteButton
|
<UserDeleteButton
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
|
import CopyOnClick from '@/components/elements/CopyOnClick';
|
||||||
import FormikSwitch from '@/components/elements/FormikSwitch';
|
import FormikSwitch from '@/components/elements/FormikSwitch';
|
||||||
|
import Input from '@/components/elements/Input';
|
||||||
|
import Label from '@/components/elements/Label';
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import tw from 'twin.macro';
|
import tw from 'twin.macro';
|
||||||
import { action, Action, createContextStore } from 'easy-peasy';
|
import { action, Action, createContextStore } from 'easy-peasy';
|
||||||
|
@ -10,7 +13,7 @@ import { bool, object, string } from 'yup';
|
||||||
import { Role } from '@/api/admin/roles/getRoles';
|
import { Role } from '@/api/admin/roles/getRoles';
|
||||||
import { Values } from '@/api/admin/users/updateUser';
|
import { Values } from '@/api/admin/users/updateUser';
|
||||||
import Button from '@/components/elements/Button';
|
import Button from '@/components/elements/Button';
|
||||||
import Field from '@/components/elements/Field';
|
import Field, { FieldRow } from '@/components/elements/Field';
|
||||||
import RoleSelect from '@/components/admin/users/RoleSelect';
|
import RoleSelect from '@/components/admin/users/RoleSelect';
|
||||||
|
|
||||||
interface ctx {
|
interface ctx {
|
||||||
|
@ -33,16 +36,18 @@ export interface Params {
|
||||||
|
|
||||||
onSubmit: (values: Values, helpers: FormikHelpers<Values>) => void;
|
onSubmit: (values: Values, helpers: FormikHelpers<Values>) => void;
|
||||||
|
|
||||||
|
uuid?: string;
|
||||||
role: Role | null;
|
role: Role | null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export default function UserForm ({ title, initialValues, children, onSubmit, role }: Params) {
|
export default function UserForm ({ title, initialValues, children, onSubmit, uuid, role }: Params) {
|
||||||
const submit = (values: Values, helpers: FormikHelpers<Values>) => {
|
const submit = (values: Values, helpers: FormikHelpers<Values>) => {
|
||||||
onSubmit(values, helpers);
|
onSubmit(values, helpers);
|
||||||
};
|
};
|
||||||
|
|
||||||
if (!initialValues) {
|
if (!initialValues) {
|
||||||
initialValues = {
|
initialValues = {
|
||||||
|
externalId: '',
|
||||||
username: '',
|
username: '',
|
||||||
email: '',
|
email: '',
|
||||||
password: '',
|
password: '',
|
||||||
|
@ -68,45 +73,56 @@ export default function UserForm ({ title, initialValues, children, onSubmit, ro
|
||||||
<SpinnerOverlay visible={isSubmitting}/>
|
<SpinnerOverlay visible={isSubmitting}/>
|
||||||
|
|
||||||
<Form css={tw`mb-0`}>
|
<Form css={tw`mb-0`}>
|
||||||
<div css={tw`md:w-full md:flex md:flex-row`}>
|
<FieldRow>
|
||||||
<div css={tw`md:w-full md:flex md:flex-col md:mr-4 mt-6 md:mt-0`}>
|
{uuid &&
|
||||||
<Field
|
<div>
|
||||||
id={'username'}
|
<Label>UUID</Label>
|
||||||
name={'username'}
|
<CopyOnClick text={uuid}>
|
||||||
label={'Username'}
|
<Input
|
||||||
type={'text'}
|
type={'text'}
|
||||||
/>
|
value={uuid}
|
||||||
</div>
|
readOnly
|
||||||
|
/>
|
||||||
<div css={tw`md:w-full md:flex md:flex-col md:ml-4 mt-6 md:mt-0`}>
|
</CopyOnClick>
|
||||||
<Field
|
</div>
|
||||||
id={'email'}
|
}
|
||||||
name={'email'}
|
<Field
|
||||||
label={'Email Address'}
|
id={'externalId'}
|
||||||
type={'email'}
|
name={'externalId'}
|
||||||
/>
|
label={'External ID'}
|
||||||
</div>
|
type={'text'}
|
||||||
</div>
|
description={'Used by external integrations, this field should not be modified unless you know what you are doing.'}
|
||||||
|
/>
|
||||||
<div css={tw`md:w-full md:flex md:flex-row mt-6`}>
|
<Field
|
||||||
<div css={tw`md:w-full md:flex md:flex-col md:mr-4 mt-6 md:mt-0`}>
|
id={'username'}
|
||||||
<Field
|
name={'username'}
|
||||||
id={'password'}
|
label={'Username'}
|
||||||
name={'password'}
|
type={'text'}
|
||||||
label={'Password'}
|
description={'The user\'s username, what else would go here?'}
|
||||||
type={'password'}
|
/>
|
||||||
placeholder={'••••••••'}
|
<Field
|
||||||
autoComplete={'new-password'}
|
id={'email'}
|
||||||
/>
|
name={'email'}
|
||||||
</div>
|
label={'Email Address'}
|
||||||
|
type={'email'}
|
||||||
<div css={tw`md:w-full md:flex md:flex-col md:ml-4 mt-6 md:mt-0`}>
|
description={'The user\'s email address, what else would go here?'}
|
||||||
<RoleSelect selected={role}/>
|
/>
|
||||||
</div>
|
<Field
|
||||||
</div>
|
id={'password'}
|
||||||
|
name={'password'}
|
||||||
|
label={'Password'}
|
||||||
|
type={'password'}
|
||||||
|
placeholder={'••••••••'}
|
||||||
|
autoComplete={'new-password'}
|
||||||
|
/* TODO: Change description depending on if user is being created or updated. */
|
||||||
|
description={'Leave empty to email the user a link where they will be required to set a password.'}
|
||||||
|
/>
|
||||||
|
<RoleSelect selected={role}/>
|
||||||
|
</FieldRow>
|
||||||
|
|
||||||
|
{/* TODO: Remove toggle once role permissions are implemented. */}
|
||||||
<div css={tw`w-full flex flex-row mb-6`}>
|
<div css={tw`w-full flex flex-row mb-6`}>
|
||||||
<div css={tw`w-full bg-neutral-800 border border-neutral-900 shadow-inner mt-6 p-4 rounded`}>
|
<div css={tw`w-full bg-neutral-800 border border-neutral-900 shadow-inner p-4 rounded`}>
|
||||||
<FormikSwitch
|
<FormikSwitch
|
||||||
name={'rootAdmin'}
|
name={'rootAdmin'}
|
||||||
label={'Root Admin'}
|
label={'Root Admin'}
|
||||||
|
|
|
@ -245,9 +245,11 @@ export const SearchableSelect = <T extends IdObj>({ id, name, label, placeholder
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={className}>
|
<div className={className}>
|
||||||
<Label htmlFor={id + '-select-label'}>{label}</Label>
|
<div css={tw`flex flex-row`}>
|
||||||
|
<Label htmlFor={id + '-select-label'}>{label}</Label>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div css={tw`relative mt-1`}>
|
<div css={tw`relative`}>
|
||||||
<InputSpinner visible={loading}>
|
<InputSpinner visible={loading}>
|
||||||
<Input
|
<Input
|
||||||
ref={searchInput}
|
ref={searchInput}
|
||||||
|
|
Loading…
Reference in a new issue