Skip to content

Commit

Permalink
fix: occurrence creation and edit view
Browse files Browse the repository at this point in the history
KK-1049.

The React-admin plugin has a special handling for validation
in the useInput-hook. That is there to prevent handling
the translations to be handled twice -- once by React-admin and
once by the input functions I suppose. To fix the translation
of the validation error message, a special handler was needed
to be used with the BoundedTextField.

Also, the occurrence edit and create views were broken,
because the validation function was set as a property for
a ReferenceInput (of React-admin), which no longer has
such a property.
  • Loading branch information
nikomakela authored and karisal-anders committed Mar 14, 2024
1 parent 8683033 commit 0a9353c
Show file tree
Hide file tree
Showing 3 changed files with 39 additions and 23 deletions.
54 changes: 35 additions & 19 deletions src/common/components/dateTimeTextField/DateTimeTextField.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import React from 'react';
import type { InputProps } from 'react-admin';
import type { InputProps, Validator } from 'react-admin';
import { useInput, useRecordContext, useTranslate } from 'react-admin';
import type { TextFieldProps } from '@mui/material/TextField';
import TextField from '@mui/material/TextField';
Expand All @@ -12,52 +12,68 @@ const useStyles = makeStyles({
textFieldInput: { width: '100%' },
});

/**
* Removes the special prefix `@@react-admin@@` and the needless quotation marks
* that might be added by the useInput-hook.
* @param message the translation key (with ra-core's special prefix to avoid double translation)
* @returns the fixed translation key
* @example
* Warning: Missing translation for key: "@@react-admin@@"occurrences.fields.time.fields.time.errorMessage""
* @example
* // a code related to the validation in the useInput.ts...
* validate: async (value, values) => {
* if (!sanitizedValidate) return true;
* const error = await sanitizedValidate(value, values, props);
* if (!error) return true;
* // react-hook-form expects errors to be plain strings but our validators can return objects
* // that have message and args.
* // To avoid double translation for users that validate with a schema instead of our validators
* // we use a special format for our validators errors.
* // The ValidationError component will check for this format and extract the message and args
* // to translate.
* return `@@react-admin@@${JSON.stringify(error)}`
*/
const handleUseInputDoubleValidationMessage = (message: string) =>
message.replace('@@react-admin@@', '').replaceAll('"', '');

export type BoundedTextFieldProps = InputProps & TextFieldProps;

const BoundedTextField = (props: BoundedTextFieldProps) => {
const translate = useTranslate();
const classes = useStyles();

const { label, variant, defaultValue, disabled } = props;
const {
field: { name, onChange },
field,
fieldState: { isTouched, error },
formState: { isSubmitted },
isRequired,
} = useInput(props);

return (
<TextField
variant={variant}
{...props}
{...field}
className={classes.textFieldInput}
size="small"
name={name}
label={label}
onChange={onChange}
error={!!(isTouched && error)}
helperText={
(isTouched || isSubmitted) && !!error
? translate(error?.message ?? '')
? translate(
handleUseInputDoubleValidationMessage(error?.message ?? '')
)
: undefined
}
required={isRequired}
defaultValue={defaultValue}
disabled={disabled}
/>
);
};

const validateDate = (value: string) => {
return moment(value, 'D.M.YYYY', true).isValid()
const validateDate: Validator = (value: string) =>
moment(value, 'D.M.YYYY', true)?.isValid()
? undefined
: 'occurrences.fields.time.fields.date.errorMessage';
};

const validateTime = (value: string) => {
return moment(value, 'H:mm', true).isValid()
const validateTime: Validator = (value: string) =>
moment(value, 'H:mm', true)?.isValid()
? undefined
: 'occurrences.fields.time.fields.time.errorMessage';
};

const DateTimeTextInput = ({
variant,
Expand Down
4 changes: 2 additions & 2 deletions src/domain/occurrences/OccurrenceCreate.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import {
SimpleForm,
SelectInput,
ReferenceInput,
required,
Loading,
} from 'react-admin';
import Grid from '@mui/material/Grid';
Expand All @@ -26,10 +25,11 @@ const OccurrenceCreateForm = () => {
label="occurrences.fields.venue.label"
source="venueId"
reference="venues"
validate={[required()]}
isRequired
fullWidth
>
<SelectInput
required
variant="outlined"
optionText="translations.FI.name"
helperText="occurrences.fields.venue.helperText"
Expand Down
4 changes: 2 additions & 2 deletions src/domain/occurrences/OccurrenceEdit.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import {
SimpleForm,
SelectInput,
ReferenceInput,
required,
Toolbar,
SaveButton,
DeleteButton,
Expand Down Expand Up @@ -75,10 +74,11 @@ const OccurrenceEditForm = () => {
label="occurrences.fields.venue.label"
source="venue.id"
reference="venues"
validate={[required()]}
isRequired
fullWidth
>
<SelectInput
required
variant="outlined"
optionText="translations.FI.name"
helperText="occurrences.fields.venue.helperText"
Expand Down

0 comments on commit 0a9353c

Please sign in to comment.