import React, { useState, useEffect } from 'react'; import { useTranslation } from 'react-i18next'; import { Paper, Typography, FormControl, Grid, Button, useTheme, makeStyles, createStyles } from '@material-ui/core'; import { useSelector, useDispatch } from 'react-redux'; import { Formik, Field, Form, FormikHelpers } from 'formik'; import { TextField, CheckboxWithLabel } from 'formik-material-ui'; import { CloudUpload } from '@material-ui/icons'; import { Skeleton } from '@material-ui/lab'; import { IExternalDeviceId } from '@energyweb/origin-backend-core'; import { areDeviceSpecificPropertiesValid, PowerFormatter, showNotification, NotificationTypeEnum, useValidation, usePermissions, Moment, FormikDatePicker, HierarchicalMultiSelect, FormInput, Requirements, DeviceSelectors, Upload, IUploadedFile, // should be removed getConfiguration, fromGeneralSelectors } from '@energyweb/origin-ui-core'; import { createDevice } from '../../features'; interface IFormValues { facilityName: string; capacity: string; commissioningDate: Moment; registrationDate: Moment; address: string; latitude: string; longitude: string; supported: boolean; projectStory: string; country: string; postalCode: string; region: string; subregion: string; } const INITIAL_FORM_VALUES: IFormValues = { facilityName: '', capacity: '', commissioningDate: null, registrationDate: null, address: '', latitude: '', longitude: '', supported: false, projectStory: '', country: '', postalCode: '', region: '', subregion: '' }; const useStyles = makeStyles(() => createStyles({ container: { padding: '10px' }, selectContainer: { paddingTop: '10px' }, fileUploadInput: { display: 'none' } }) ); export const RegisterDevice = () => { // should be removed const configuration = useSelector(getConfiguration); // const compliance = useSelector(getCompliance); const country = useSelector(fromGeneralSelectors.getCountry); const backendClient = useSelector(fromGeneralSelectors.getBackendClient); const externalDeviceIdTypes = useSelector(fromGeneralSelectors.getExternalDeviceIdTypes); const environment = useSelector(fromGeneralSelectors.getEnvironment); const dispatch = useDispatch(); const { t } = useTranslation(); const { Yup, yupLocaleInitialized } = useValidation(); const [selectedDeviceType, setSelectedDeviceType] = useState([]); const [selectedLocation, setSelectedLocation] = useState([]); const [selectedGridOperator, setSelectedGridOperator] = useState([]); const [imagesUploaded, setImagesUploaded] = useState(false); /* eslint-disable-next-line @typescript-eslint/no-unused-vars */ const [imagesUploadedList, setImagesUploadedList] = useState([]); const { canAccessPage } = usePermissions(); /* eslint-disable-next-line @typescript-eslint/no-unused-vars */ const [docfiles, setFiles] = useState([]); // check if needed? // const uploadedDocFiles = docfiles // .filter((f) => !f.removed && f.uploadedName) // .reduce( // (arr, x) => { // arr.filenames.push(x.uploadedName); // return arr; // }, // { filenames: [] } // ); const classes = useStyles(useTheme()); const [externalIdSchema, setExternalIdSchema] = useState({}); useEffect(() => { if (externalDeviceIdTypes) { const requiredDeviceIdTypes = externalDeviceIdTypes.filter( (id) => id?.required && !id?.autogenerated ); for (const externalId of requiredDeviceIdTypes) { setExternalIdSchema({ ...externalIdSchema, [externalId.type]: Yup.string().required() }); } } }, [externalDeviceIdTypes]); const VALIDATION_SCHEMA = Yup.object().shape({ facilityName: Yup.string().label(t('device.properties.facilityName')).required(), capacity: Yup.number().label(t('device.properties.capacity')).required().positive(), commissioningDate: Yup.date().required(), registrationDate: Yup.date().required(), address: Yup.string().label(t('device.properties.address')).required(), latitude: Yup.number().label(t('device.properties.latitude')).required().min(-90).max(90), longitude: Yup.number() .label(t('device.properties.longitude')) .required() .min(-180) .max(180), supported: Yup.boolean(), projectStory: Yup.string(), ...externalIdSchema }); async function submitForm( values: typeof INITIAL_FORM_VALUES, formikActions: FormikHelpers ): Promise { const deviceType = selectedDeviceType.sort((a, b) => b.length - a.length)[0]; formikActions.setSubmitting(true); const externalDeviceIds: IExternalDeviceId[] = externalDeviceIdTypes.map(({ type }) => { return { id: values[type], type }; }); dispatch( createDevice({ name: values.facilityName, code: '', defaultAccount: '', deviceType, fuelType: '', countryCode: country, capacity: PowerFormatter.getBaseValueFromValueInDisplayUnit( parseFloat(values.capacity) ), commissioningDate: values.commissioningDate.toISOString(), registrationDate: values.registrationDate.toISOString(), address: values.address, latitude: values.latitude, longitude: values.longitude, timezone: 'Asia/Bangkok', gridOperator: (selectedGridOperator && selectedGridOperator[0]) || '', notes: '', smartMeterId: '', description: values.projectStory, externalDeviceIds, imageIds: [''], postalCode: values.postalCode, region: values.region, subregion: values.subregion }) ); formikActions.setSubmitting(false); } async function uploadImages(files: FileList) { if (files.length > 10) { showNotification( t('device.feedback.pleaseSelectUpToXImages', { limit: 10, actual: files.length }), NotificationTypeEnum.Error ); return; } try { const { data: uploadedFiles } = await backendClient.fileClient.upload( Array.from(files) as Blob[] ); setImagesUploaded(true); setImagesUploadedList(uploadedFiles); } catch (error) { console.log(error); showNotification( t('device.feedback.unexpectedErrorWhenUploadingImages'), NotificationTypeEnum.Error ); } } if (!configuration || !yupLocaleInitialized) { return ; } if (!canAccessPage?.value) { return ; } const initialFormValues: IFormValues = INITIAL_FORM_VALUES; return ( {(formikProps) => { const { isValid, isSubmitting, setFieldValue, validateField } = formikProps; const fieldDisabled = isSubmitting; const buttonDisabled = isSubmitting || !isValid || selectedDeviceType.length === 0 || !areDeviceSpecificPropertiesValid( selectedLocation, selectedGridOperator, environment ); return (
{t('device.info.general')}
setSelectedDeviceType(value) } allValues={configuration.deviceTypeService.deviceTypes} selectOptions={[ { label: t('device.properties.deviceType'), placeholder: t('device.info.selectDeviceType') }, { label: t('device.properties.deviceType'), placeholder: t('device.info.selectDeviceType') }, { label: t('device.properties.deviceType'), placeholder: t('device.info.selectDeviceType') } ]} disabled={fieldDisabled} singleChoice={true} required={true} />
{ const parsedValue = parseFloat( (e.target as any)?.value ); if (!isNaN(parsedValue)) { setFieldValue( 'latitude', parsedValue.toFixed(2) ); } validateField('latitude'); } }} /> { const parsedValue = parseFloat( (e.target as any)?.value ); if (!isNaN(parsedValue)) { setFieldValue( 'longitude', parsedValue.toFixed(2) ); } validateField('longitude'); } }} />
{t('device.properties.story')} {externalDeviceIdTypes.map((externalDeviceIdType, index) => { if (externalDeviceIdType.autogenerated) { return null; } return ( ); })} {t('device.properties.images')} {imagesUploaded ? (

{t('device.feedback.imagesUploaded')}

{t('device.info.pleaseFillOtherFields')}

) : ( <> uploadImages(e.target.files)} multiple disabled={imagesUploaded} /> )} { setFiles(newFiles); }} />
); }}
); };