fix(frontend): apply feedback updates

This commit is contained in:
yassinedorbozgithub 2025-02-03 11:21:05 +01:00
parent 51c3a88d01
commit 2ba5c6660a
4 changed files with 53 additions and 82 deletions

View File

@ -1,11 +1,12 @@
/* /*
* Copyright © 2024 Hexastack. All rights reserved. * Copyright © 2025 Hexastack. All rights reserved.
* *
* Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms: * Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms:
* 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission. * 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission.
* 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file). * 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file).
*/ */
import { Dialog, DialogActions, DialogContent } from "@mui/material"; import { Dialog, DialogActions, DialogContent } from "@mui/material";
import { DialogTitle } from "@/app-components/dialogs"; import { DialogTitle } from "@/app-components/dialogs";
@ -16,7 +17,7 @@ import { FormButtons } from "../buttons/FormButtons";
export const FormDialog = <T,>({ export const FormDialog = <T,>({
title, title,
children, children,
onConfirm, onSubmit,
...rest ...rest
}: FormDialogProps<T>) => { }: FormDialogProps<T>) => {
return ( return (
@ -26,9 +27,9 @@ export const FormDialog = <T,>({
</DialogTitle> </DialogTitle>
<DialogContent>{children}</DialogContent> <DialogContent>{children}</DialogContent>
<DialogActions> <DialogActions>
<FormButtons<T> <FormButtons
onCancel={() => rest.onClose?.({}, "backdropClick")} onCancel={() => rest.onClose?.({}, "backdropClick")}
onConfirm={onConfirm} onConfirm={onSubmit}
/> />
</DialogActions> </DialogActions>
</Dialog> </Dialog>

View File

@ -1,17 +1,13 @@
/* /*
* Copyright © 2024 Hexastack. All rights reserved. * Copyright © 2025 Hexastack. All rights reserved.
* *
* Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms: * Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms:
* 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission. * 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission.
* 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file). * 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file).
*/ */
import {
BaseSyntheticEvent, import React, { BaseSyntheticEvent, FC, useEffect } from "react";
forwardRef,
useEffect,
useImperativeHandle,
} from "react";
import { useForm } from "react-hook-form"; import { useForm } from "react-hook-form";
import { ContentContainer } from "@/app-components/dialogs/layouts/ContentContainer"; import { ContentContainer } from "@/app-components/dialogs/layouts/ContentContainer";
@ -23,16 +19,14 @@ import { useToast } from "@/hooks/useToast";
import { useTranslate } from "@/hooks/useTranslate"; import { useTranslate } from "@/hooks/useTranslate";
import { EntityType } from "@/services/types"; import { EntityType } from "@/services/types";
import { ICategory, ICategoryAttributes } from "@/types/category.types"; import { ICategory, ICategoryAttributes } from "@/types/category.types";
import { import { ComponentFormProps } from "@/types/common/dialogs.types";
ComponentFormProps,
HTMLFormElementExtension,
HTMLFormElementExtra,
} from "@/types/common/dialogs.types";
export const CategoryForm = forwardRef< export const CategoryForm: FC<ComponentFormProps<ICategory>> = ({
HTMLFormElement, data,
ComponentFormProps<ICategory> FormWrapper = React.Fragment,
>(({ data, ...rest }, ref) => { FormWrapperProps,
...rest
}) => {
const { t } = useTranslate(); const { t } = useTranslate();
const { toast } = useToast(); const { toast } = useToast();
const options = { const options = {
@ -81,13 +75,6 @@ export const CategoryForm = forwardRef<
}); });
}; };
useImperativeHandle<
HTMLFormElementExtension<ICategory>,
HTMLFormElementExtra<ICategory>
>(ref, () => ({
submitAsync,
}));
useEffect(() => { useEffect(() => {
if (data) { if (data) {
reset({ reset({
@ -99,19 +86,25 @@ export const CategoryForm = forwardRef<
}, [data, reset]); }, [data, reset]);
return ( return (
<form ref={ref} onSubmit={submitAsync}> <FormWrapper
<ContentContainer> open={!!FormWrapperProps?.open}
<ContentItem> onSubmit={submitAsync}
<Input {...FormWrapperProps}
label={t("placeholder.label")} >
{...register("label", validationRules.label)} <form onSubmit={submitAsync}>
autoFocus <ContentContainer>
helperText={errors.label ? errors.label.message : null} <ContentItem>
/> <Input
</ContentItem> label={t("placeholder.label")}
</ContentContainer> {...register("label", validationRules.label)}
</form> autoFocus
helperText={errors.label ? errors.label.message : null}
/>
</ContentItem>
</ContentContainer>
</form>
</FormWrapper>
); );
}); };
CategoryForm.displayName = "CategoryForm"; CategoryForm.displayName = "CategoryForm";

View File

@ -1,20 +1,16 @@
/* /*
* Copyright © 2024 Hexastack. All rights reserved. * Copyright © 2025 Hexastack. All rights reserved.
* *
* Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms: * Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms:
* 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission. * 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission.
* 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file). * 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file).
*/ */
import { useRef } from "react";
import { FormDialog } from "@/app-components/dialogs"; import { FormDialog } from "@/app-components/dialogs";
import { useTranslate } from "@/hooks/useTranslate"; import { useTranslate } from "@/hooks/useTranslate";
import { ICategory } from "@/types/category.types"; import { ICategory } from "@/types/category.types";
import { import { ComponentFormDialogProps } from "@/types/common/dialogs.types";
ComponentFormDialogProps,
HTMLFormElementExtra,
} from "@/types/common/dialogs.types";
import { CategoryForm } from "./CategoryForm"; import { CategoryForm } from "./CategoryForm";
@ -23,25 +19,18 @@ export const CategoryFormDialog = <T extends ICategory = ICategory>({
...rest ...rest
}: ComponentFormDialogProps<T>) => { }: ComponentFormDialogProps<T>) => {
const { t } = useTranslate(); const { t } = useTranslate();
const formRef = useRef<(HTMLFormElement & HTMLFormElementExtra<T>) | null>(
null,
);
return ( return (
<FormDialog<T> <CategoryForm
title={payload ? t("title.edit_category") : t("title.new_category")} data={payload}
onConfirm={async (e) => { onSuccess={() => {
return await formRef.current?.submitAsync(e); rest.onClose(true);
}} }}
{...rest} FormWrapper={FormDialog}
> FormWrapperProps={{
<CategoryForm title: payload ? t("title.edit_category") : t("title.new_category"),
ref={formRef} ...rest,
data={payload} }}
onSuccess={() => { />
rest.onClose(true);
}}
/>
</FormDialog>
); );
}; };

View File

@ -7,7 +7,7 @@
*/ */
import { DialogProps as MuiDialogProps } from "@mui/material"; import { DialogProps as MuiDialogProps } from "@mui/material";
import { BaseSyntheticEvent, ReactNode } from "react"; import { BaseSyntheticEvent } from "react";
// context // context
@ -139,11 +139,9 @@ export interface DialogProviderProps {
// form dialog // form dialog
export interface FormDialogProps<T> extends MuiDialogProps { export interface FormDialogProps<T> extends MuiDialogProps {
title: string; title?: string;
children: ReactNode; children?: React.ReactNode;
onConfirm: ( onSubmit: (e: BaseSyntheticEvent) => Promise<T>;
e: BaseSyntheticEvent<object, any, any>,
) => Promise<T | undefined>;
} }
// form // form
@ -151,23 +149,13 @@ export type ComponentFormProps<T> = {
data: T | null; data: T | null;
onError?: () => void; onError?: () => void;
onSuccess?: () => void; onSuccess?: () => void;
FormWrapper?: React.FC<FormDialogProps<T>>;
FormWrapperProps?: Partial<FormDialogProps<T>>;
}; };
export interface FormButtonsProps<T> { export interface FormButtonsProps<T> {
onCancel?: () => void; onCancel?: () => void;
onConfirm?: ( onConfirm: (e: BaseSyntheticEvent) => Promise<T>;
e: BaseSyntheticEvent<object, any, any>,
) => Promise<T | undefined>;
} }
export type HTMLFormElementExtra<T> = {
submitAsync: (
e: BaseSyntheticEvent<object, any, any>,
) => Promise<T | undefined>;
};
export type HTMLFormElementExtension<T> =
| HTMLFormElement
| HTMLFormElementExtra<T>;
export type ComponentFormDialogProps<T> = DialogProps<T | null, boolean>; export type ComponentFormDialogProps<T> = DialogProps<T | null, boolean>;