import { useMutation, useQuery } from "@apollo/client"; import { useEffect, useState } from "react"; import { Button, Card, Checkbox, Form, Space, Table } from "antd"; import { useTranslation } from "react-i18next"; import { connect } from "react-redux"; import { createStructuredSelector } from "reselect"; import { selectCurrentUser } from "../../redux/user/user.selectors"; import AlertComponent from "../alert/alert.component"; import { QUERY_NOTIFICATION_SETTINGS, UPDATE_NOTIFICATION_SETTINGS } from "../../graphql/user.queries.js"; import { notificationScenarios } from "../../utils/jobNotificationScenarios.js"; import LoadingSpinner from "../loading-spinner/loading-spinner.component.jsx"; import PropTypes from "prop-types"; import { useNotification } from "../../contexts/Notifications/notificationContext.jsx"; import ColumnHeaderCheckbox from "../notification-settings/column-header-checkbox.component.jsx"; /** * Notifications Settings Form * @param currentUser * @returns {JSX.Element} * @constructor */ const NotificationSettingsForm = ({ currentUser }) => { const { t } = useTranslation(); const [form] = Form.useForm(); const [initialValues, setInitialValues] = useState({}); const [isDirty, setIsDirty] = useState(false); const notification = useNotification(); // Fetch notification settings. const { loading, error, data } = useQuery(QUERY_NOTIFICATION_SETTINGS, { fetchPolicy: "network-only", nextFetchPolicy: "network-only", variables: { email: currentUser.email }, skip: !currentUser }); const [updateNotificationSettings, { loading: saving }] = useMutation(UPDATE_NOTIFICATION_SETTINGS); // Populate form with fetched data. useEffect(() => { if (data?.associations?.length > 0) { const settings = data.associations[0].notification_settings || {}; // Ensure each scenario has an object with { app, email, fcm }. const formattedValues = notificationScenarios.reduce((acc, scenario) => { acc[scenario] = settings[scenario] ?? { app: false, email: false, fcm: false }; return acc; }, {}); setInitialValues(formattedValues); form.setFieldsValue(formattedValues); setIsDirty(false); // Reset dirty state when new data loads. } }, [data, form]); const handleSave = async (values) => { if (data?.associations?.length > 0) { const userId = data.associations[0].id; // Save the updated notification settings. const result = await updateNotificationSettings({ variables: { id: userId, ns: values } }); if (!result?.errors) { notification.success({ message: t("notifications.labels.notification-settings-success") }); setInitialValues(values); setIsDirty(false); } else { notification.error({ message: t("notifications.labels.notification-settings-failure") }); } } }; // Mark the form as dirty on any manual change. const handleFormChange = () => { setIsDirty(true); }; const handleReset = () => { form.setFieldsValue(initialValues); setIsDirty(false); }; if (error) return ; if (loading) return ; const columns = [ { title: t("notifications.labels.scenario"), dataIndex: "scenarioLabel", key: "scenario", render: (_, record) => t(`notifications.scenarios.${record.key}`), width: "90%" }, { title: setIsDirty(true)} />, dataIndex: "app", key: "app", align: "center", render: (_, record) => ( ) }, { title: setIsDirty(true)} />, dataIndex: "email", key: "email", align: "center", render: (_, record) => ( ) } // TODO: Disabled for now until FCM is implemented. // { // title: setIsDirty(true)} />, // dataIndex: "fcm", // key: "fcm", // align: "center", // render: (_, record) => ( // // // // ) // } ]; const dataSource = notificationScenarios.map((scenario) => ({ key: scenario })); return (
} > ); }; NotificationSettingsForm.propTypes = { currentUser: PropTypes.shape({ email: PropTypes.string.isRequired }).isRequired }; const mapStateToProps = createStructuredSelector({ currentUser: selectCurrentUser }); export default connect(mapStateToProps)(NotificationSettingsForm);