Skip to content

Commit

Permalink
feat: use debounced mutation in create-project and add saving indicator
Browse files Browse the repository at this point in the history
  • Loading branch information
matthieu-foucault committed Dec 13, 2021
1 parent 701117f commit 7ee171e
Show file tree
Hide file tree
Showing 2 changed files with 102 additions and 21 deletions.
50 changes: 50 additions & 0 deletions app/components/Form/SavingIndicator.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import { faSync, faCheck } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";

interface Props {
isSaved: boolean;
lastEdited: Date;
}

const SavingIndicator: React.FC<Props> = ({ isSaved, lastEdited }) => {
return (
<div>
<span className="last-edited">
Last edited:{" "}
{lastEdited.toLocaleString("en-CA", {
timeZone: "America/Vancouver",
dateStyle: "short",
})}
</span>
<span>
<FontAwesomeIcon icon={isSaved ? faCheck : faSync} />
<span className="is-saved">
{isSaved ? "Changes saved." : "Saving changes..."}
</span>
</span>
<style jsx>
{`
div {
display: inline-flex;
justify-content: flex-end;
align-items: baseline;
color: #939393;
border: solid 1px #939393;
border-radius: 4px;
padding: 0.5rem;
}
.last-edited {
margin-right: 1rem;
}
.is-saved {
margin-left: 0.5rem;
}
`}
</style>
</div>
);
};

export default SavingIndicator;
73 changes: 52 additions & 21 deletions app/pages/cif/create-project.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,16 @@ import { withRelay, RelayProps } from "relay-nextjs";
import { graphql, usePreloadedQuery } from "react-relay/hooks";
import { createProjectQuery } from "__generated__/createProjectQuery.graphql";
import withRelayOptions from "lib/relay/withRelayOptions";
import updateFormChangeMutation from "mutations/FormChange/updateFormChange";
import updateFormChangeMutation, {
mutation,
} from "mutations/FormChange/updateFormChange";
import { useRouter } from "next/router";
import ProjectForm from "components/Project/ProjectForm";
import { Button } from "@button-inc/bcgov-theme";
import Grid from "@button-inc/bcgov-theme/Grid";
import { useState } from "react";
import { useMemo, useState } from "react";
import useDebouncedMutation from "mutations/useDebouncedMutation";
import SavingIndicator from "components/Form/SavingIndicator";

const CreateProjectQuery = graphql`
query createProjectQuery($id: ID!) {
Expand All @@ -19,6 +23,7 @@ const CreateProjectQuery = graphql`
formChange(id: $id) {
id
newFormData
updatedAt
}
}
}
Expand All @@ -31,29 +36,38 @@ export function CreateProject({
const { query } = usePreloadedQuery(CreateProjectQuery, preloadedQuery);

const [errors, setErrors] = useState({});

const [updateFormChange, updatingFormChange] = useDebouncedMutation(mutation);
const lastEditedDate = useMemo(
() => new Date(query.formChange.updatedAt),
[query.formChange.updatedAt]
);
if (!query.formChange.id) return null;

// Function: stage the change data in the form_change table
const storeResult = async (data) => {
const variables = {
input: {
id: query.formChange.id,
formChangePatch: {
newFormData: data,
},
},
};
await updateFormChangeMutation(preloadedQuery.environment, variables);
};

// The applyChangeFromComponent function will require this page to be aware of the state of the newFormData object
const formChangeData = query.formChange.newFormData;

// A function to be called by individual components making changes to the overall form_change data
const applyChangesFromComponent = (changeObject: any) => {
const handleChange = (changeObject: any) => {
const updatedFormData = { ...formChangeData, ...changeObject };
storeResult(updatedFormData);
return updateFormChange({
variables: {
input: {
id: query.formChange.id,
formChangePatch: {
newFormData: updatedFormData,
},
},
},
optimisticResponse: {
updateFormChange: {
formChange: {
id: query.formChange.id,
newFormData: updatedFormData,
},
},
},
debounceKey: query.formChange.id,
});
};

const onFormErrors = (incomingErrors: {}) => {
Expand All @@ -74,14 +88,24 @@ export function CreateProject({
};

return (
<DefaultLayout session={query.session} title="CIF Projects Management">
<h1>Create Project</h1>
<DefaultLayout
session={query.session}
title="CIF Projects Management"
width="wide"
>
<header>
<h2>Project Overview</h2>
<SavingIndicator
isSaved={!updatingFormChange}
lastEdited={lastEditedDate}
/>
</header>
<Grid cols={2}>
<Grid.Row>
<Grid.Col>
<ProjectForm
formData={query.formChange.newFormData}
onChange={applyChangesFromComponent}
onChange={handleChange}
onFormErrors={onFormErrors}
/>
</Grid.Col>
Expand All @@ -96,6 +120,13 @@ export function CreateProject({
Commit Project Changes
</Button>
</Grid>
<style jsx>{`
header {
display: flex;
justify-content: space-between;
align-items: start;
}
`}</style>
</DefaultLayout>
);
}
Expand Down

0 comments on commit 7ee171e

Please sign in to comment.