Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rework housing update side menu #1107

Open
wants to merge 35 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
f0fcb3c
feat(frontend): add AppSelectNext to replace AppSelect
Falinor Jan 16, 2025
c58de4f
feat(frontend): add AsideNext to replace Aside
Falinor Jan 16, 2025
7f7207c
feat(frontend): refactor HousingEditionSideMenu
Falinor Jan 16, 2025
9befb65
feat(frontend): correctly set margins
Falinor Jan 20, 2025
0e62411
feat: add the mobilization tab
Falinor Jan 20, 2025
396e0df
feat(frontend): add the note tab
Falinor Jan 20, 2025
fde0b64
feat(schemas): add HousingUpdatePayloadDTO’s schema
Falinor Jan 21, 2025
b6b8af1
refactor(models): set some HousingUpdatePayloadDTO keys as nullable
Falinor Jan 21, 2025
61371ee
feat(server): implement unit of work using knex transactions
Falinor Jan 21, 2025
f35d9db
feat: implement a basic housing update endpoint
Falinor Jan 21, 2025
4e65183
feat(schemas): add the note payload schema
Falinor Jan 21, 2025
1b9b9ad
feat(server): add hasRole middleware
Falinor Jan 22, 2025
d3134ec
feat(schemas): add id validator
Falinor Jan 22, 2025
6871a79
feat: add note creation endpoint
Falinor Jan 22, 2025
447a69d
refactor(server): rename some note repository’s functions
Falinor Jan 22, 2025
41b95d6
test(server): test note repository creation
Falinor Jan 22, 2025
3c9c8d1
refactor(server): add deprecated fields actually existing in the note…
Falinor Jan 22, 2025
87eeaf6
feat(server): fail note creation if the housing was not found
Falinor Jan 22, 2025
79da7d4
feat(frontend): add note creation endpoint
Falinor Jan 22, 2025
263a6af
refactor(server): change note kind value
Falinor Jan 22, 2025
b44d273
refactor: rename housing note list endpoint; remove listByOwnerId; re…
Falinor Jan 22, 2025
c8f5cfa
feat(frontend): add notifications on housing update and note creation…
Falinor Jan 22, 2025
4da8158
feat(frontend): hide AsideNext’s backdrop
Falinor Jan 22, 2025
ee9fd37
feat(frontend): make AsideNext’s vertical overflow scrollable
Falinor Jan 22, 2025
bbcb4da
refactor(frontend): move housing update to the side menu component
Falinor Jan 22, 2025
7f04f28
test(frontend): test note creation; test housing update
Falinor Jan 22, 2025
7186992
fix(schemas): forbid sending empty strings
Falinor Jan 22, 2025
555d7b3
feat(server): validate housing update inputs
Falinor Jan 22, 2025
2738918
feat(server): create events when a housing is updated
Falinor Jan 22, 2025
c7a164b
build(frontend): fix build error
Falinor Jan 22, 2025
4f27f22
fix(frontend): fix AppSelectNext types
Falinor Jan 22, 2025
1ac50f9
fix(frontend): disable select animation
Falinor Jan 22, 2025
a44b0ca
fix(frontend): invalidate events when updating a housing
Falinor Jan 22, 2025
99b3afe
fix(frontend): reset the housing edition form on side menu close
Falinor Jan 23, 2025
f7fedc4
test(frontend): fix housing update tests
Falinor Jan 23, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
75 changes: 75 additions & 0 deletions frontend/src/components/Aside/AsideNext.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import { fr } from '@codegouvfr/react-dsfr';
import Button from '@codegouvfr/react-dsfr/Button';
import ButtonsGroup from '@codegouvfr/react-dsfr/ButtonsGroup';
import Drawer, { DrawerProps } from '@mui/material/Drawer';
import Grid from '@mui/material/Unstable_Grid2';
import { ReactNode } from 'react';

interface AsideProps {
drawerProps?: Omit<DrawerProps, 'open' | 'onClose'>;
header?: ReactNode;
main?: ReactNode;
footer?: ReactNode;
open: boolean;
onClose(): void;
onSave(): void;
}

function Aside(props: AsideProps) {
return (
<Drawer
anchor="right"
open={props.open}
onClose={props.onClose}
slotProps={{
backdrop: {
invisible: true
}
}}
{...props.drawerProps}
>
<Grid container sx={{ flexDirection: 'column' }} xs>
<Grid container sx={{ justifyContent: 'space-between', mb: 3 }}>
{props.header && <Grid xs>{props.header}</Grid>}

<Grid xs="auto">
<Button
iconId="fr-icon-close-line"
priority="tertiary no outline"
onClick={props.onClose}
>
Fermer
</Button>
</Grid>
</Grid>

<Grid sx={{ overflowY: 'auto' }} xs>
{props.main}
</Grid>

<Grid className={fr.cx('fr-mt-3w', 'fr-mb-1w')}>
<hr style={{ margin: `0 -${fr.spacing('3w')}` }} />
{props.footer ?? (
<ButtonsGroup
buttons={[
{
priority: 'secondary',
children: 'Annuler',
onClick: props.onClose
},
{
priority: 'primary',
children: 'Enregistrer',
onClick: props.onSave
}
]}
inlineLayoutWhen="always"
/>
)}
</Grid>
</Grid>
</Drawer>
);
}

export default Aside;
62 changes: 19 additions & 43 deletions frontend/src/components/HousingDetails/HousingDetailsCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,17 @@ import classNames from 'classnames';
import { useState } from 'react';

import styles from './housing-details-card.module.scss';
import { Housing, HousingUpdate } from '../../models/Housing';
import { Housing } from '../../models/Housing';
import HousingDetailsSubCardBuilding from './HousingDetailsSubCardBuilding';
import HousingDetailsSubCardProperties from './HousingDetailsSubCardProperties';
import HousingDetailsSubCardLocation from './HousingDetailsSubCardLocation';
import EventsHistory from '../EventsHistory/EventsHistory';
import { Event } from '../../models/Event';
import HousingEditionSideMenu from '../HousingEdition/HousingEditionSideMenu';
import { useFindNotesByHousingQuery } from '../../services/note.service';
import { useFindEventsByHousingQuery } from '../../services/event.service';
import { Note } from '../../models/Note';
import HousingDetailsCardOccupancy from './HousingDetailsSubCardOccupancy';
import HousingDetailsCardMobilisation from './HousingDetailsSubCardMobilisation';
import { Campaign } from '../../models/Campaign';
import { useUpdateHousingMutation } from '../../services/housing.service';
import AppLink from '../_app/AppLink/AppLink';
import { useUser } from '../../hooks/useUser';

Expand All @@ -39,32 +36,9 @@ function HousingDetailsCard({
housingCampaigns
}: Props) {
const { isVisitor } = useUser();
const [updateHousing] = useUpdateHousingMutation();

const [isHousingListEditionExpand, setIsHousingListEditionExpand] =
useState(false);

const { refetch: refetchHousingEvents } = useFindEventsByHousingQuery(
housing.id
);
const { refetch: refetchHousingNotes } = useFindNotesByHousingQuery(
housing.id
);

const submitHousingUpdate = async (
housing: Housing,
housingUpdate: HousingUpdate
) => {
await updateHousing({
housing,
housingUpdate
});
await refetchHousingEvents();
await refetchHousingNotes();

setIsHousingListEditionExpand(false);
};

return (
<Paper component="article" elevation={0} sx={{ padding: 3 }}>
<Grid component="header" container sx={{ mb: 2 }}>
Expand Down Expand Up @@ -100,7 +74,6 @@ function HousingDetailsCard({
<HousingEditionSideMenu
housing={housing}
expand={isHousingListEditionExpand}
onSubmit={submitHousingUpdate}
onClose={() => setIsHousingListEditionExpand(false)}
/>
</>
Expand All @@ -111,21 +84,24 @@ function HousingDetailsCard({
<>
<HousingDetailsCardOccupancy
housing={housing}
lastOccupancyEvent={housing.source !== 'datafoncier-import' ? housingEvents.find(
(event) =>
event.category === 'Followup' &&
event.kind === 'Update' &&
event.section === 'Situation' &&
event.name === "Modification du statut d'occupation" &&
event.old.occupancy !== event.new.occupancy
) :
housingEvents.find(
(event) =>
event.category === 'Group' &&
event.kind === 'Create' &&
event.section === 'Ajout d’un logement dans un groupe' &&
event.name === "Ajout dans un groupe"
)}
lastOccupancyEvent={
housing.source !== 'datafoncier-import'
? housingEvents.find(
(event) =>
event.category === 'Followup' &&
event.kind === 'Update' &&
event.section === 'Situation' &&
event.name === "Modification du statut d'occupation" &&
event.old.occupancy !== event.new.occupancy
)
: housingEvents.find(
(event) =>
event.category === 'Group' &&
event.kind === 'Create' &&
event.section === 'Ajout d’un logement dans un groupe' &&
event.name === 'Ajout dans un groupe'
)
}
/>
<HousingDetailsCardMobilisation
housing={housing}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@ import Badge from '@codegouvfr/react-dsfr/Badge';
import Tag from '@codegouvfr/react-dsfr/Tag';
import Typography from '@mui/material/Typography';
import Grid from '@mui/material/Unstable_Grid2';
import classNames from 'classnames';
import { getYear } from 'date-fns';

import {
getOccupancy,
getSource,
Expand All @@ -12,10 +15,8 @@ import {
} from '../../models/Housing';
import HousingDetailsSubCard from './HousingDetailsSubCard';
import DPE from '../DPE/DPE';
import classNames from 'classnames';
import styles from './housing-details-card.module.scss';
import { Event } from '../../models/Event';
import { getYear } from 'date-fns';
import LabelNext from '../Label/LabelNext';

interface Props {
Expand Down Expand Up @@ -57,7 +58,7 @@ function HousingDetailsCardOccupancy({ housing, lastOccupancyEvent }: Props) {
>
Occupation :
</Typography>
<Badge className="bg-975">
<Badge aria-label="Occupation" className="bg-975">
{OccupancyKindLabels[getOccupancy(housing.occupancy)]}
</Badge>
</Grid>
Expand Down
Loading
Loading