frontend/app/multistep/projectcreate_new/TemplateComponent.tsx (136 lines of code) (raw):

import React, { useEffect, useState } from "react"; import axios from "axios"; import { SystemNotification, SystemNotifcationKind, } from "@guardian/pluto-headers"; import { LinearProgress, MenuItem, Select, TextField, Typography, } from "@material-ui/core"; import { projectCreateStyles } from "./CommonStyles"; import { useGuardianStyles } from "~/misc/utils"; interface TemplateComponentProps { templateValue?: number; templateValueDidChange: (newValue: number) => void; } const TemplateComponent: React.FC<TemplateComponentProps> = (props) => { const [knownProjectTemplates, setKnownProjectTemplates] = useState< ProjectTemplate[] >([]); const [defaultProjectTemplate, setDefaultProjectTemplate] = useState< number | undefined >(undefined); const [loading, setLoading] = useState(true); const classes = projectCreateStyles(); const guardianClasses = useGuardianStyles(); //load in project type data at mount useEffect(() => { const loadDefaultProjectType = async () => { setLoading(true); const response = await axios.get<PlutoApiResponse<PlutoDefault>>( "/api/default/project_template_id", { validateStatus: () => true } ); if (response.status == 200) { try { const numericId = parseInt(response.data.result.value); setDefaultProjectTemplate(numericId); } catch (err) { console.error("Could not get default project template id: ", err); } } else if (response.status != 404) { SystemNotification.open( SystemNotifcationKind.Error, "Could not load default project template" ); } }; const loadInData = async () => { setLoading(true); const response = await axios.get<PlutoApiResponse<ProjectTemplate[]>>( "/api/template", { validateStatus: () => true } ); setLoading(false); switch (response.status) { case 200: if (response.data.result.length == 0) { console.error( "There are no project templates defined so we can't create a project" ); SystemNotification.open( SystemNotifcationKind.Error, "There are no project templates defined in the system" ); } setKnownProjectTemplates( response.data.result.filter((template) => !template.deprecated) ); break; default: console.error( "Could not load in project types: server said ", response.status, " ", response.data ); SystemNotification.open( SystemNotifcationKind.Error, "Could not load in project types" ); } }; loadDefaultProjectType() .then(() => loadInData()) .catch((err) => { console.error(err); SystemNotification.open( SystemNotifcationKind.Error, "Could not set up template selector" ); }); }, []); //ensure that we have _a_ current value set if the known projects change useEffect(() => { if (!props.templateValue && knownProjectTemplates.length > 0) { const defaultValue = defaultProjectTemplate ?? knownProjectTemplates[0].id; props.templateValueDidChange(defaultValue); } }, [knownProjectTemplates]); return ( <div> <div> {props.templateValue ? ( <TextField select style={{ width: 340 }} label="Project template" helperText="Please select a project template" value={props.templateValue} onChange={(evt) => props.templateValueDidChange( (evt.target.value as unknown) as number ) } FormHelperTextProps={{ style: { fontSize: "0.86rem" } }} InputLabelProps={{ shrink: true, style: { fontSize: "1.2rem" } }} > {knownProjectTemplates.map((template, idx) => ( <MenuItem value={template.id} key={idx}> {template.name} </MenuItem> ))} </TextField> ) : null} {loading ? <LinearProgress /> : null} {!loading && !props.templateValue ? ( <Typography>No project templates available</Typography> ) : null} </div> </div> ); }; export default TemplateComponent;