Compare commits

..

No commits in common. "eb36e9cebbf511097e3cd1e3bbbaae91f65c0d33" and "c6c0958a3f1c72dbc2698a0dd964556a3efc9b72" have entirely different histories.

29 changed files with 107 additions and 170 deletions

1
.env
View File

@ -1 +0,0 @@
VITE_BASE_URL="https://nerd-back.point-dev.net/api/"

View File

@ -1 +0,0 @@
REACT_APP_BASE_URL=

1
package-lock.json generated
View File

@ -12782,6 +12782,7 @@
"version": "2.0.15", "version": "2.0.15",
"resolved": "https://registry.npmjs.org/react-qr-code/-/react-qr-code-2.0.15.tgz", "resolved": "https://registry.npmjs.org/react-qr-code/-/react-qr-code-2.0.15.tgz",
"integrity": "sha512-MkZcjEXqVKqXEIMVE0mbcGgDpkfSdd8zhuzXEl9QzYeNcw8Hq2oVIzDLWuZN2PQBwM5PWjc2S31K8Q1UbcFMfw==", "integrity": "sha512-MkZcjEXqVKqXEIMVE0mbcGgDpkfSdd8zhuzXEl9QzYeNcw8Hq2oVIzDLWuZN2PQBwM5PWjc2S31K8Q1UbcFMfw==",
"license": "MIT",
"dependencies": { "dependencies": {
"prop-types": "^15.8.1", "prop-types": "^15.8.1",
"qr.js": "0.0.0" "qr.js": "0.0.0"

View File

@ -33,7 +33,7 @@ const App = () => {
/> />
{renderRoutesRecursively(menuItems)} {renderRoutesRecursively(menuItems)}
{CrudRoute.map((route) => { {CrudRoute.map((route) => {
const useAbility = hasAbility(route.abilities, route.abilities_value); const useAbility = hasAbility(route.abilities, route.abilities_value);
if (!RoleByType(route)) { if (!RoleByType(route)) {

View File

@ -10,7 +10,6 @@ export const renderRoutesRecursively = (routes: TMenuItem[]) =>
if (!useAbility) { if (!useAbility) {
return false; return false;
} }
return ( return (
<React.Fragment key={route.path}> <React.Fragment key={route.path}>
<Route path={route.path} element={RenderRouteElement(route)} /> <Route path={route.path} element={RenderRouteElement(route)} />

View File

@ -1,22 +0,0 @@
import { Tooltip } from 'antd'
import React from 'react'
import { useTranslation } from 'react-i18next';
import { FaPaperclip } from 'react-icons/fa'
interface ReportButtonsProps {
editTooltipTitle?: any;
onClick?: () => void;
}
const ReportTableIcon = ({editTooltipTitle,onClick}:ReportButtonsProps) => {
const {t} = useTranslation();
return (
<Tooltip placement="top" title={t(editTooltipTitle)} color="#E0E0E0">
<span onClick={onClick}>
<FaPaperclip size={22} style={{ color: "#A098AE" }} />
</span>
</Tooltip>
)
}
export default ReportTableIcon

View File

@ -14,8 +14,7 @@ const PageHeader = ({
pageTitle, pageTitle,
openModel = true, openModel = true,
locationToNavigate, locationToNavigate,
addModal = true, addModal = true
modelButtonTitle = "add",
}: { }: {
canAdd?: any; canAdd?: any;
ModelAbility?: any; ModelAbility?: any;
@ -23,7 +22,6 @@ const PageHeader = ({
openModel?: boolean; openModel?: boolean;
locationToNavigate?: string | any; locationToNavigate?: string | any;
addModal?:boolean; addModal?:boolean;
modelButtonTitle?:string
}) => { }) => {
const navigate = useNavigate(); const navigate = useNavigate();
const { handel_open_model } = useModalHandler(); const { handel_open_model } = useModalHandler();
@ -59,7 +57,7 @@ const PageHeader = ({
className="add_button" className="add_button"
> >
<BsPlusCircleFill /> <BsPlusCircleFill />
{t(`practical.${modelButtonTitle}`)} {t(`practical.add`)}
</button> </button>
</div> </div>
) :""} ) :""}

View File

@ -42,7 +42,7 @@ const QrCodeModels: React.FC<ModalFormProps> = ({
<main className="main_modal"> <main className="main_modal">
<div className="ValidationField w-100 mb-5 "> <div className="ValidationField w-100 mb-5 ">
<QRCodeGenerator url = {`https://nerd-back.point-dev.net/api/students/question`} serial={objectToEdit?.serial}/> <QRCodeGenerator url = {`https://nerd-back.point-dev.net/api/students/question`} serial={objectToEdit.serial}/>
</div> </div>
</main> </main>
</Modal> </Modal>

View File

@ -32,9 +32,7 @@ const TableHeader = () => {
pageTitle="notification" pageTitle="notification"
ModelAbility={ModalEnum?.NOTIFICATION_ADD} ModelAbility={ModalEnum?.NOTIFICATION_ADD}
canAdd={canAddNotification} canAdd={canAddNotification}
modelButtonTitle="add_notification"
/> />
<FilterLayout sub_children={<FilterForm />} filterTitle="table.notification" /> <FilterLayout sub_children={<FilterForm />} filterTitle="table.notification" />
<Table /> <Table />
<AddModalForm /> <AddModalForm />

View File

@ -40,11 +40,19 @@ export const useColumns = () => {
const columns: TableColumnsType<Notification> = [ const columns: TableColumnsType<Notification> = [
{ {
title: t("columns.created_at"), title: t("columns.id"),
dataIndex: "created_at", dataIndex: "id",
key: "created_at", key: "id",
align: "center", align: "center",
render: (_text, record) => record?.created_at, render: (_text, record) => record?.id,
},
{
title: `${t("columns.body")}`,
dataIndex: "body",
key: "body",
align: "center",
render: (_text, record) => record?.body,
ellipsis:true
}, },
{ {
title: `${t("columns.seen")}`, title: `${t("columns.seen")}`,
@ -54,14 +62,6 @@ export const useColumns = () => {
render: (_text, record) => record?.seen, render: (_text, record) => record?.seen,
ellipsis:true ellipsis:true
}, },
{
title: `${t("columns.title")}`,
dataIndex: "title",
key: "title",
align: "center",
render: (_text, record) => record?.title,
ellipsis:true
},
{ {
title: `${t("columns.notifiable_type")}`, title: `${t("columns.notifiable_type")}`,
dataIndex: "notifiable_type", dataIndex: "notifiable_type",
@ -71,12 +71,23 @@ export const useColumns = () => {
ellipsis:true ellipsis:true
}, },
{ {
title: `${t("columns.body")}`,
dataIndex: "body", title: t("columns.procedure"),
key: "body", key: "actions",
align: "center", align: "center",
render: (_text, record) => record?.body, width: "25vw",
// ellipsis:true render: (_text, record, index) => {
return (
<ActionButtons
canDelete={canDeleteNotification}
canEdit={canEditNotification}
index={index}
onDelete={() => handelDelete(record)}
onEdit={() => handleEdit(record)}
onShow={() => handelShow(record)}
/>
);
},
}, },
]; ];

View File

@ -1,7 +1,11 @@
import TrashButton from "../../../Components/Ui/TrashButton"
import { notifications } from "../../../types/Notifications" import { notifications } from "../../../types/Notifications"
const Card = ({name,date,image,id}:notifications) => { const Card = ({name,date,image,id,pop,setPop}:notifications) => {
const handleDeleteOne = () => {
setPop(pop?.filter((item:any)=> item?.id !== id))
}
return ( return (
<div className="notification_card" key={id}> <div className="notification_card" key={id}>
@ -12,6 +16,12 @@ const Card = ({name,date,image,id}:notifications) => {
<p>{date}</p> <p>{date}</p>
</div> </div>
</div> </div>
<div>
<TrashButton
onClick={handleDeleteOne}
name="delete"
icon={false}/>
</div>
</div> </div>
) )
} }

View File

@ -1,32 +1,48 @@
import { Divider } from 'antd'; import { Divider } from 'antd';
import { useTranslation } from 'react-i18next' import { useTranslation } from 'react-i18next'
import { NotificationArray } from './NotificationArray';
import { notifications } from '../../../types/Notifications'; import { notifications } from '../../../types/Notifications';
import Card from './Card'; import Card from './Card';
import { useGetAllNotificationMine } from '../../../api/notification'; import TrashButton from '../../../Components/Ui/TrashButton';
import { useEffect, useState } from 'react';
const Page = () => { const Page = () => {
const {t} = useTranslation(); const {t} = useTranslation();
const {data} = useGetAllNotificationMine(); const [pop, setPop] = useState(NotificationArray);
console.log(data); const [isEmpty, setIsEmpty] = useState(pop.length < 1 ? true : false);
const handleDeleteAll = () => {
setPop([])
}
useEffect(()=>{
if(pop.length < 1){
setIsEmpty(true);
}else{
setIsEmpty(false);
}
},[pop])
return ( return (
<div className='notification_container'> <div className='notification_container'>
<div className='notification_header'> <div className='notification_header'>
<h3>{t("header.notifications")}</h3> <h3>{t("header.notifications")}</h3>
<TrashButton
onClick={handleDeleteAll}
name='delete_all'/>
</div> </div>
<Divider/> <Divider/>
{ {
!!data?.data isEmpty === false
? ?
<div className="notification_body"> <div className="notification_body">
{data?.data?.map((not:notifications)=>( {pop?.map((not:notifications)=>(
<Card <Card
id={not?.id} id={not?.id}
name={not?.name} name={not?.name}
date={not?.date} date={not?.date}
image={not?.image} pop={pop}
/> setPop={setPop}
image={not?.image}/>
))} ))}
</div> </div>
: :

View File

@ -12,9 +12,6 @@ import {
} from "../../../utils/hasAbilityFn"; } from "../../../utils/hasAbilityFn";
import ActionButtons from "../../../Components/Table/ActionButtons"; import ActionButtons from "../../../Components/Table/ActionButtons";
import { useFilterStateState } from "../../../zustand/Filter"; import { useFilterStateState } from "../../../zustand/Filter";
import { FaPaperclip } from "react-icons/fa";
import { ParamsEnum } from "../../../enums/params";
import ReportTableIcon from "../../../Components/Ui/ReportTableIcon";
export const useColumns = () => { export const useColumns = () => {
const { setObjectToEdit } = useObjectToEdit((state) => state); const { setObjectToEdit } = useObjectToEdit((state) => state);
@ -27,13 +24,6 @@ export const useColumns = () => {
setIsOpen(ModalEnum?.QUESTION_DELETE); setIsOpen(ModalEnum?.QUESTION_DELETE);
}; };
const handleNavigateToReport = (record: any) => {
setFilter({})
// console.log(record);
navigate(`/report/${record?.report?.id}`);
};
const handleEdit = (record: any) => { const handleEdit = (record: any) => {
console.log(record,"record"); console.log(record,"record");
const lesson = record?.lessons?.[0] ; const lesson = record?.lessons?.[0] ;
@ -180,9 +170,8 @@ export const useColumns = () => {
key: "actions", key: "actions",
align: "center", align: "center",
render: ({_text, record, index}:any) => { render: (_text, record, index) => {
return ( return (
<div className="flex">
<ActionButtons <ActionButtons
canDelete={canDeleteQuestion} canDelete={canDeleteQuestion}
canEdit={canEditQuestion} canEdit={canEditQuestion}
@ -190,12 +179,6 @@ export const useColumns = () => {
onDelete={() => handelDelete(record)} onDelete={() => handelDelete(record)}
onEdit={() => handleEdit(record)} onEdit={() => handleEdit(record)}
/> />
{
!!record?.report?.content
? <ReportTableIcon editTooltipTitle='practical.with_report' onClick={() => handleNavigateToReport(record)}/>
: ""
}
</div>
); );
}, },
}, },

View File

@ -10,7 +10,6 @@ const ReportInfo = () => {
const {data} = useGetAllReport({ const {data} = useGetAllReport({
show:report_id show:report_id
}) })
const {t} = useTranslation(); const {t} = useTranslation();
return ( return (

View File

@ -4,23 +4,19 @@ import { useColumns } from "./useTableColumns";
import { useGetAllReport } from "../../../api/report"; import { useGetAllReport } from "../../../api/report";
import { useFilterState } from "../../../Components/Utils/Filter/FilterState"; import { useFilterState } from "../../../Components/Utils/Filter/FilterState";
import { useFilterStateState } from "../../../zustand/Filter"; import { useFilterStateState } from "../../../zustand/Filter";
import { useParams } from "react-router-dom";
import { ParamsEnum } from "../../../enums/params";
const App: React.FC = () => { const App: React.FC = () => {
const { filterState } = useFilterState(); const { filterState } = useFilterState();
const { Filter } = useFilterStateState(); const { Filter } = useFilterStateState();
const name = Filter?.name ; const name = Filter?.name ;
const sort_by = Filter?.sort_by ; const sort_by = Filter?.sort_by ;
const { question_id } = useParams<ParamsEnum>();
const response = useGetAllReport({ const response = useGetAllReport({
name, name,
sort_by, sort_by,
pagination: true, pagination: true,
...filterState, ...filterState,
question_id:question_id
}); });
return <DataTable response={response} useColumns={useColumns} />; return <DataTable response={response} useColumns={useColumns} />;

View File

@ -49,14 +49,14 @@ const TableHeader = () => {
validationSchema={getValidationSchema} validationSchema={getValidationSchema}
onSubmit={handleSubmit} onSubmit={handleSubmit}
> >
{({ dirty }) => ( {({ resetForm }) => (
<Form className="Form_details_container"> <Form className="Form_details_container">
<PersonalDetailsForm /> <PersonalDetailsForm />
<TitleDetailsForm /> <TitleDetailsForm />
<AttachmentForm /> <AttachmentForm />
<div className="resellerButton"> <div className="resellerButton">
<button type="button" onClick={() => Navigate('/reseller')}>{t("practical.cancel")}</button> <button type="button" onClick={() => Navigate('/reseller')}>{t("practical.cancel")}</button>
<button type="submit" disabled={!dirty}> <button type="submit">
{t("practical.add")} {t("models.reseller")} {t("practical.add")} {t("models.reseller")}
{status === QueryStatusEnum.LOADING && ( {status === QueryStatusEnum.LOADING && (
<span className="Spinier_Div"> <span className="Spinier_Div">

View File

@ -25,6 +25,7 @@ const TableHeader = ({canEdit,ModelAbility}:{canEdit?: any;ModelAbility?: any;})
useSetPageTitle(t(`page_header.add_reseller`)); useSetPageTitle(t(`page_header.add_reseller`));
const handleSubmit = (values: any) => { const handleSubmit = (values: any) => {
console.log(values);
const DataToSend = { const DataToSend = {
...values, ...values,
@ -61,14 +62,14 @@ const TableHeader = ({canEdit,ModelAbility}:{canEdit?: any;ModelAbility?: any;})
validationSchema={getValidationSchema} validationSchema={getValidationSchema}
onSubmit={handleSubmit} onSubmit={handleSubmit}
> >
{({ dirty }) => ( {({ resetForm }) => (
<Form className="Form_details_container"> <Form className="Form_details_container">
<PersonalDetailsForm isEdit={true} /> <PersonalDetailsForm isEdit={true} />
<TitleDetailsForm /> <TitleDetailsForm />
<AttachmentForm /> <AttachmentForm />
<div className="resellerButton"> <div className="resellerButton">
<button type="button" onClick={()=>Navigate('/reseller')}>{t("practical.cancel")}</button> <button type="button" onClick={()=>Navigate('/reseller')}>{t("practical.cancel")}</button>
<button type="submit" disabled={!dirty}> <button type="submit">
{t("practical.edit")} {t("models.reseller")} {t("practical.edit")} {t("models.reseller")}
{status === QueryStatusEnum.LOADING && ( {status === QueryStatusEnum.LOADING && (
<span className=" reseller_spinner_div"> <span className=" reseller_spinner_div">

View File

@ -8,17 +8,15 @@ import { FormValues } from "../../types/Auth";
import { useTranslation } from "react-i18next"; import { useTranslation } from "react-i18next";
import { getLocalStorage } from "../../utils/LocalStorage"; import { getLocalStorage } from "../../utils/LocalStorage";
import { USER_KEY } from "../../config/AppKey"; import { USER_KEY } from "../../config/AppKey";
import { toast } from "react-toastify";
const LoginForm = () => { const LoginForm = () => {
const { mutate, isLoading, isSuccess, data } = useLoginAdmin(); const { mutate, isLoading, isSuccess, data } = useLoginAdmin();
const [t] = useTranslation(); const [t] = useTranslation();
const handelSubmit = (values: FormValues) => { const handelSubmit = (values: FormValues) => {
mutate(values); mutate(values);
// localStorage.setItem('type',) // localStorage.setItem('type',)
}; };
const { login } = useAuthState(); const { login } = useAuthState();
const LoginData = { const LoginData = {

View File

@ -165,7 +165,7 @@ export const menuItems: TMenuItem[] = [
element: <Report />, element: <Report />,
icon: <FaPaperclip />, icon: <FaPaperclip />,
text: "sidebar.report", text: "sidebar.report",
path: `/${ABILITIES_ENUM?.Report}` , path: `/${ABILITIES_ENUM?.Report}`,
abilities: ABILITIES_ENUM?.Report, abilities: ABILITIES_ENUM?.Report,
abilities_value: ABILITIES_VALUES_ENUM.INDEX, abilities_value: ABILITIES_VALUES_ENUM.INDEX,
prevPath: 0, prevPath: 0,
@ -439,15 +439,6 @@ export const CrudRoute: TCrudRoute[] = [
prevPath: 0, prevPath: 0,
}, },
// report based on question id
{
header: "page_header.report",
element: <Report />,
path: `/${ABILITIES_ENUM?.Report}/${ParamsEnum?.QUESTION_ID}` ,
abilities: ABILITIES_ENUM?.Report,
abilities_value: ABILITIES_VALUES_ENUM.INDEX,
prevPath: 0,
},
]; ];
export const AppRoutes: Record<string, string> = Object.fromEntries( export const AppRoutes: Record<string, string> = Object.fromEntries(

View File

@ -4,7 +4,6 @@
padding: 20px 2vw; padding: 20px 2vw;
border-radius: 10px; border-radius: 10px;
} }
.TowItemField { .TowItemField {
display: flex; display: flex;
gap: 4%; gap: 4%;
@ -13,7 +12,6 @@
width: 48%; width: 48%;
} }
} }
.small_section { .small_section {
background: var(--bg); background: var(--bg);
@include Shadow; @include Shadow;
@ -318,4 +316,3 @@ button:disabled {
height: 40px; height: 40px;
} }
} }

View File

@ -105,29 +105,19 @@
} }
} }
.reseller_spinner_div { .reseller_spinner_div{
z-index: 999;
position: absolute; position: absolute;
width: 100% !important; width: 70% !important;
height: 100%; height: 80%;
top: 50%; top: 50%;
left: 40%; left: 40%;
transform: translate(-50%, -50%); transform: translate(-50%, -50%);
backdrop-filter: blur(1px); /* Adds the blur effect */ background: var(--primary);
display: flex; display: flex;
align-items: center; align-items: center;
justify-content: center; justify-content: center;
.ant-spin .ant-spin-dot-item { .ant-spin .ant-spin-dot-item {
width: 25px; background: white !important;
height: 25px;
background: var(--primary) !important;
}
.ant-spin .ant-spin-dot{
font-size: 30px;
width: 60px;
height: 60px;
} }
} }

View File

@ -1,5 +1,4 @@
export const BaseURL = "https://nerd-back.point-dev.net/api/"; export const BaseURL = "https://nerd-back.point-dev.net/api/";
// export const BaseURL = "http://192.168.43.153:8080/api/"; // export const BaseURL = "http://192.168.43.153:8080/api/";
// export const BaseURL = import.meta.env.VITE_BASE_URL ;
export const HEADER_KEY = "X-Custom-Query-Key"; export const HEADER_KEY = "X-Custom-Query-Key";

View File

@ -36,14 +36,13 @@ function useAxios() {
const method = response.config.method; const method = response.config.method;
const key = response.config.headers[HEADER_KEY]; const key = response.config.headers[HEADER_KEY];
const isToasted = response.config.headers["X-Custom-Message"]; const isToasted = response.config.headers["X-Custom-Message"];
const ResponseMessage = const ResponseMessage =
responseMsg || t("validation.the_possess_done_successful"); responseMsg || t("validation.the_possess_done_successful");
if (method !== AxiosQueryEnum?.GET) { if (method !== AxiosQueryEnum?.GET) {
queryClient.invalidateQueries(key); queryClient.invalidateQueries(key);
if (isToasted) { if (isToasted) {
toast.success(ResponseMessage); toast.success(ResponseMessage);
} }
setValidation([{}]); setValidation([{}]);
@ -53,18 +52,15 @@ function useAxios() {
function (error) { function (error) {
// Reject errors with non-2xx status codes // Reject errors with non-2xx status codes
const status = error?.response?.status; const status = error?.response?.status;
// console.log(status); if (status >= 400) {
return Promise.reject(error);
// if (status >= 400) { }
// return Promise.reject(error);
// }
const errorMsg = error?.response?.data?.error; const errorMsg = error?.response?.data?.error;
const errorField = error?.response?.data; const errorField = error?.response?.data;
const method = error.config.method; const method = error.config.method;
if (status === AxiosStatusEnum.VALIDATION) { if (status === AxiosStatusEnum.VALIDATION) {
setValidation(errorMsg ?? errorField); setValidation(errorMsg ?? errorField);
const ErrorKey = Object?.keys(errorMsg)?.[0]; const ErrorKey = Object?.keys(errorMsg)?.[0];
const isString = const isString =
@ -72,7 +68,6 @@ function useAxios() {
? errorMsg ? errorMsg
: errorMsg?.[ErrorKey]?.[0] ?? : errorMsg?.[ErrorKey]?.[0] ??
t("validation.some_thing_went_wrong"); t("validation.some_thing_went_wrong");
toast.error(t(`${isString}`)); toast.error(t(`${isString}`));
return; return;
} }
@ -87,7 +82,7 @@ function useAxios() {
return Promise.reject(error); return Promise.reject(error);
} }
// return Promise.reject(error); // Important to reject the promise return Promise.reject(error); // Important to reject the promise
} }
); );

View File

@ -5,14 +5,12 @@ import useUpdateMutation from "./helper/useUpdateMutation";
const API = { const API = {
GET: "/notification", GET: "/notification",
GET_MINE: "/notification/mine",
ADD: "/notification", ADD: "/notification",
DELETE: "/notification", DELETE: "/notification",
UPDATE: "/notification", UPDATE: "/notification",
}; };
const KEY = "notification"; const KEY = "notification";
const KEY_Mine = "notification_mine";
export const useGetAllNotification = (params?: any, options?: any) => export const useGetAllNotification = (params?: any, options?: any) =>
useGetQuery(KEY, API.GET, params, options); useGetQuery(KEY, API.GET, params, options);
@ -20,7 +18,3 @@ export const useAddNotification = () => useAddMutation(KEY, API.ADD);
export const useUpdateNotification = (params?: any) => useUpdateMutation(KEY, API.GET); export const useUpdateNotification = (params?: any) => useUpdateMutation(KEY, API.GET);
export const useDeleteNotification = (params?: any) => export const useDeleteNotification = (params?: any) =>
useDeleteMutation(KEY, API.DELETE); useDeleteMutation(KEY, API.DELETE);
export const useGetAllNotificationMine = (params?: any, options?: any) =>
useGetQuery(KEY_Mine, API.GET_MINE, params, options);

View File

@ -10,4 +10,4 @@ const I18nProvider: React.FC<I18nProviderProps> = ({ children }) => {
return <I18nextProvider i18n={i18n}>{children}</I18nextProvider>; return <I18nextProvider i18n={i18n}>{children}</I18nextProvider>;
}; };
export default I18nProvider; export default I18nProvider;

View File

@ -244,10 +244,7 @@
"lesson":"الدرس", "lesson":"الدرس",
"code":"رمز", "code":"رمز",
"due_to":"صالح الى", "due_to":"صالح الى",
"question_name":"اسم السؤال", "question_name":"اسم السؤال"
"body":"نص الإشعار",
"seen":"عدد المستخدمين",
"notifiable_type":"المستخدمون"
}, },
"practical": { "practical": {
"to_confirm_deletion_please_re_enter": "لتأكيد الحذف، يرجى إعادة الإدخال", "to_confirm_deletion_please_re_enter": "لتأكيد الحذف، يرجى إعادة الإدخال",
@ -332,9 +329,7 @@
"show_collection":"حصيلة", "show_collection":"حصيلة",
"does_not_exist_notification":"عذرا لا يوجد إشعارات...", "does_not_exist_notification":"عذرا لا يوجد إشعارات...",
"student_name":"اسم الطالب", "student_name":"اسم الطالب",
"report_content":"محتوى التقرير", "report_content":"محتوى التقرير"
"with_report":"يوجد تقرير",
"add_notification":"إرسال إشعار"
}, },
"Table": { "Table": {
"header": "", "header": "",
@ -431,7 +426,7 @@
"show_collection":"حصيلة", "show_collection":"حصيلة",
"city":"مدينة", "city":"مدينة",
"financialCollection":"التحصيلات", "financialCollection":"التحصيلات",
"notification":"إدارة الاشعارات" "notification":"الاشعارات"
}, },
"education_class_actions": { "education_class_actions": {
"Student_Records": "سجلات الطلاب", "Student_Records": "سجلات الطلاب",
@ -575,10 +570,7 @@
"expiration_date":"تاريخ الالغاء", "expiration_date":"تاريخ الالغاء",
"package":"حزمة", "package":"حزمة",
"contact_number":"رقم الهاتف", "contact_number":"رقم الهاتف",
"question_content":"محتوى السؤال", "question_content":"محتوى السؤال"
"body":"النص",
"seen":"شوهدت",
"notifiable_type":"نوع الاشعار"
}, },
"select": { "select": {
"enums": { "enums": {
@ -918,7 +910,7 @@
"city":"مدينة", "city":"مدينة",
"coupon":"قسيمة", "coupon":"قسيمة",
"financial_collection":"التحصيلات", "financial_collection":"التحصيلات",
"notification":"إدارة الاشعارات" "notification":"الاشعارات"
}, },
"message": { "message": {
"some_thing_went_wrong": "حدث خطأ ما", "some_thing_went_wrong": "حدث خطأ ما",
@ -971,7 +963,7 @@
"Coupon":"قسيمة", "Coupon":"قسيمة",
"financial_collection":"التحصيلات", "financial_collection":"التحصيلات",
"show_collection":"حصيلة", "show_collection":"حصيلة",
"notification":"إدارة الاشعارات" "notification":"الاشعارات"
}, },
"page_header": { "page_header": {
"home": "لوحة القيادة", "home": "لوحة القيادة",
@ -1030,7 +1022,7 @@
"questionBank":"بنك الأسئلة", "questionBank":"بنك الأسئلة",
"roles":"الدور", "roles":"الدور",
"coupon":"قسيمة", "coupon":"قسيمة",
"notification":"إدارة الاشعارات" "notification":"الاشعارات"
}, },
"table": { "table": {
"student": "قائمة الطلاب", "student": "قائمة الطلاب",

View File

@ -9,6 +9,6 @@ export interface Notification {
body:string; body:string;
seen:string; seen:string;
notifiable_type:string; notifiable_type:string;
created_at:string
} }

View File

@ -3,4 +3,6 @@ export type notifications = {
name:string, name:string,
date:string, date:string,
image:string, image:string,
setPop?:any,
pop?:any,
} }

View File

@ -1,7 +1,7 @@
import { defineConfig } from "vite"; import { defineConfig } from "vite";
import react from "@vitejs/plugin-react"; import react from "@vitejs/plugin-react";
import { visualizer } from "rollup-plugin-visualizer"; import { visualizer } from "rollup-plugin-visualizer";
import env from "vite-plugin-env-compatible";
export default defineConfig(() => { export default defineConfig(() => {
return { return {
@ -9,27 +9,18 @@ export default defineConfig(() => {
outDir: "build", outDir: "build",
rollupOptions: { rollupOptions: {
output: { output: {
entryFileNames: "[name].[hash].js", entryFileNames: '[name].[hash].js',
chunkFileNames: "[name].[hash].js", chunkFileNames: '[name].[hash].js',
assetFileNames: "[name].[hash][extname]", assetFileNames: '[name].[hash][extname]',
}, },
},
}, },
envPrefix: "VITE_",
css: {
preprocessorOptions: {
scss: {
// Optionally add a global import here for variables or mixins
// additionalData: `@import "src/styles/variables.scss";`,
},
},
}, },
plugins: [ plugins: [
react(), react(),
env(),
visualizer({ visualizer({
filename: "./bundle-analysis.html", filename: "./bundle-analysis.html", // Output file
open: true, open: true, // Open the generated file automatically
}), }),
], ],
}; };