Compare commits

..

15 Commits

Author SHA1 Message Date
738dee1f0c Update Rust crate thiserror to 1.0.48
All checks were successful
continuous-integration/drone/push Build is passing
continuous-integration/drone/pr Build is passing
2023-09-03 00:26:17 +00:00
7f0ea4f04c Update Rust crate redis to 0.23.3
All checks were successful
continuous-integration/drone/pr Build is passing
continuous-integration/drone/push Build is passing
2023-09-02 00:27:12 +00:00
49d27e5849 Update dependency @types/node to v16.18.46
All checks were successful
continuous-integration/drone/push Build is passing
2023-09-01 01:17:31 +00:00
03b9dfc60a Update dependency @mui/material to v5.14.7
Some checks failed
continuous-integration/drone/pr Build is passing
continuous-integration/drone/push Build is failing
2023-09-01 00:35:31 +00:00
433f8384a0 Emphasis missing mother and father
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-31 20:39:17 +02:00
2c0b6356b6 Fix bug 2023-08-31 20:36:33 +02:00
c6c984c34c Handle particular cases in simple family tree
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-31 20:26:34 +02:00
c84fb50087 Fix type declaration issue 2023-08-31 20:14:36 +02:00
79ce616781 Show a feedback when saving couple information
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-31 19:30:16 +02:00
e4a1817d7f Simplify navigation to set member photo 2023-08-31 19:27:14 +02:00
2a69c89065 Automatically trim values before saving 2023-08-31 19:23:21 +02:00
0899835fab Update dependency @mui/lab to v5.0.0-alpha.142
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-31 00:58:23 +00:00
cf5848491b Update dependency @fontsource/roboto to v5.0.8
Some checks failed
continuous-integration/drone/pr Build is passing
continuous-integration/drone/push Build is failing
2023-08-31 00:26:52 +00:00
33748e3233 Update Rust crate thiserror to 1.0.47
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-30 00:55:47 +00:00
cc0b6a2547 Update Rust crate actix-multipart to 0.6.1
Some checks failed
continuous-integration/drone/pr Build is passing
continuous-integration/drone/push Build is failing
2023-08-30 00:26:46 +00:00
9 changed files with 212 additions and 122 deletions

View File

@ -2004,11 +2004,11 @@
"integrity": "sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA==" "integrity": "sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA=="
}, },
"node_modules/@babel/runtime": { "node_modules/@babel/runtime": {
"version": "7.22.6", "version": "7.22.11",
"resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.22.6.tgz", "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.22.11.tgz",
"integrity": "sha512-wDb5pWm4WDdF6LFUde3Jl8WzPA+3ZbxYqkC6xAXuD3irdEHN1k0NfTRrJD8ZD378SJ61miMLCqIOXYhd8x+AJQ==", "integrity": "sha512-ee7jVNlWN09+KftVOu9n7S8gQzD/Z6hN/I8VBRXW4P1+Xe7kJGXMwu8vds4aGIMHZnNbdpSWCfZZtinytpcAvA==",
"dependencies": { "dependencies": {
"regenerator-runtime": "^0.13.11" "regenerator-runtime": "^0.14.0"
}, },
"engines": { "engines": {
"node": ">=6.9.0" "node": ">=6.9.0"
@ -2026,6 +2026,11 @@
"node": ">=6.9.0" "node": ">=6.9.0"
} }
}, },
"node_modules/@babel/runtime/node_modules/regenerator-runtime": {
"version": "0.14.0",
"resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.0.tgz",
"integrity": "sha512-srw17NI0TUWHuGa5CFGGmhfNIeja30WMBfbslPNhf6JrqQlLN5gcrvig1oqPxiVaXb0oW0XRKtH6Nngs5lKCIA=="
},
"node_modules/@babel/template": { "node_modules/@babel/template": {
"version": "7.22.5", "version": "7.22.5",
"resolved": "https://registry.npmjs.org/@babel/template/-/template-7.22.5.tgz", "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.22.5.tgz",
@ -2573,10 +2578,44 @@
"node": "^12.22.0 || ^14.17.0 || >=16.0.0" "node": "^12.22.0 || ^14.17.0 || >=16.0.0"
} }
}, },
"node_modules/@floating-ui/core": {
"version": "1.4.1",
"resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.4.1.tgz",
"integrity": "sha512-jk3WqquEJRlcyu7997NtR5PibI+y5bi+LS3hPmguVClypenMsCY3CBa3LAQnozRCtCrYWSEtAdiskpamuJRFOQ==",
"dependencies": {
"@floating-ui/utils": "^0.1.1"
}
},
"node_modules/@floating-ui/dom": {
"version": "1.5.1",
"resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.5.1.tgz",
"integrity": "sha512-KwvVcPSXg6mQygvA1TjbN/gh///36kKtllIF8SUm0qpFj8+rvYrpvlYdL1JoA71SHpDqgSSdGOSoQ0Mp3uY5aw==",
"dependencies": {
"@floating-ui/core": "^1.4.1",
"@floating-ui/utils": "^0.1.1"
}
},
"node_modules/@floating-ui/react-dom": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.2.tgz",
"integrity": "sha512-5qhlDvjaLmAst/rKb3VdlCinwTF4EYMiVxuuc/HVUjs46W0zgtbMmAZ1UTsDrRTxRmUEzl92mOtWbeeXL26lSQ==",
"dependencies": {
"@floating-ui/dom": "^1.5.1"
},
"peerDependencies": {
"react": ">=16.8.0",
"react-dom": ">=16.8.0"
}
},
"node_modules/@floating-ui/utils": {
"version": "0.1.1",
"resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.1.1.tgz",
"integrity": "sha512-m0G6wlnhm/AX0H12IOWtK8gASEMffnX08RtKkCgTdHb9JpHKGloI7icFfLg9ZmQeavcvR0PKmzxClyuFPSjKWw=="
},
"node_modules/@fontsource/roboto": { "node_modules/@fontsource/roboto": {
"version": "5.0.4", "version": "5.0.8",
"resolved": "https://registry.npmjs.org/@fontsource/roboto/-/roboto-5.0.4.tgz", "resolved": "https://registry.npmjs.org/@fontsource/roboto/-/roboto-5.0.8.tgz",
"integrity": "sha512-4aVlY+8u/8V15zP8Z4tscGebdD62trVo1CVNW8OsvLWYduebFxxETj7yzfkR/131fVGy/lO1RTeLf6CT7eD8CQ==" "integrity": "sha512-XxPltXs5R31D6UZeLIV1td3wTXU3jzd3f2DLsXI8tytMGBkIsGcc9sIyiupRtA8y73HAhuSCeweOoBqf6DbWCA=="
}, },
"node_modules/@humanwhocodes/config-array": { "node_modules/@humanwhocodes/config-array": {
"version": "0.11.10", "version": "0.11.10",
@ -3035,14 +3074,15 @@
} }
}, },
"node_modules/@mui/base": { "node_modules/@mui/base": {
"version": "5.0.0-beta.11", "version": "5.0.0-beta.13",
"resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.11.tgz", "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.13.tgz",
"integrity": "sha512-FdKZGPd8qmC3ZNke7CNhzcEgToc02M6WYZc9hcBsNQ17bgAd3s9F//1bDDYgMVBYxDM71V0sv/hBHlOY4I1ZVA==", "integrity": "sha512-uC0l97pBspfDAp+iz2cJq8YZ8Sd9i73V77+WzUiOAckIVEyCm5dyVDZCCO2/phmzckVEeZCGcytybkjMQuhPQw==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.22.6", "@babel/runtime": "^7.22.10",
"@emotion/is-prop-valid": "^1.2.1", "@emotion/is-prop-valid": "^1.2.1",
"@floating-ui/react-dom": "^2.0.1",
"@mui/types": "^7.2.4", "@mui/types": "^7.2.4",
"@mui/utils": "^5.14.5", "@mui/utils": "^5.14.7",
"@popperjs/core": "^2.11.8", "@popperjs/core": "^2.11.8",
"clsx": "^2.0.0", "clsx": "^2.0.0",
"prop-types": "^15.8.1", "prop-types": "^15.8.1",
@ -3075,9 +3115,9 @@
} }
}, },
"node_modules/@mui/core-downloads-tracker": { "node_modules/@mui/core-downloads-tracker": {
"version": "5.14.5", "version": "5.14.7",
"resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.5.tgz", "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.7.tgz",
"integrity": "sha512-+wpGH1USwPcKMFPMvXqYPC6fEvhxM3FzxC8lyDiNK/imLyyJ6y2DPb1Oue7OGIKJWBmYBqrWWtfovrxd1aJHTA==", "integrity": "sha512-sCWTUNElBPgB30iLvWe3PU7SIlTKZNf6/E/sko85iHVeHCM6WPkDw+y89CrZYjhFNmPqt2fIQM/pZu+rP2lFLA==",
"funding": { "funding": {
"type": "opencollective", "type": "opencollective",
"url": "https://opencollective.com/mui" "url": "https://opencollective.com/mui"
@ -3109,15 +3149,15 @@
} }
}, },
"node_modules/@mui/lab": { "node_modules/@mui/lab": {
"version": "5.0.0-alpha.140", "version": "5.0.0-alpha.142",
"resolved": "https://registry.npmjs.org/@mui/lab/-/lab-5.0.0-alpha.140.tgz", "resolved": "https://registry.npmjs.org/@mui/lab/-/lab-5.0.0-alpha.142.tgz",
"integrity": "sha512-k75jos6jklCD8tA20PAK2H4RSCKycTcR4Pbfz7JbdxIkWXJ+y2MRalwMcen1vpB99v0yZHNUo6BtGz6rvs2jlQ==", "integrity": "sha512-JDrT5G3QBZ0nzkKMFWzJY5KN8WcyDx4p7qOjg6hs7yKLq90VSdsqIOmyhvWDxJR7zPNQjo0WRYBAaRaQ5FlGxg==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.22.6", "@babel/runtime": "^7.22.10",
"@mui/base": "5.0.0-beta.11", "@mui/base": "5.0.0-beta.13",
"@mui/system": "^5.14.5", "@mui/system": "^5.14.7",
"@mui/types": "^7.2.4", "@mui/types": "^7.2.4",
"@mui/utils": "^5.14.5", "@mui/utils": "^5.14.7",
"clsx": "^2.0.0", "clsx": "^2.0.0",
"prop-types": "^15.8.1", "prop-types": "^15.8.1",
"react-is": "^18.2.0" "react-is": "^18.2.0"
@ -3158,16 +3198,16 @@
} }
}, },
"node_modules/@mui/material": { "node_modules/@mui/material": {
"version": "5.14.5", "version": "5.14.7",
"resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.5.tgz", "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.7.tgz",
"integrity": "sha512-4qa4GMfuZH0Ai3mttk5ccXP8a3sf7aPlAJwyMrUSz6h9hPri6BPou94zeu3rENhhmKLby9S/W1y+pmficy8JKA==", "integrity": "sha512-jIZj9F7zMv6IlyaYDVv5M2Kp20jIX8c0kzuwteySHS/A0IvPVyomQEPtWc51MCbpDNCqzwoZUp3rQtA2lI8k7A==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.22.6", "@babel/runtime": "^7.22.10",
"@mui/base": "5.0.0-beta.11", "@mui/base": "5.0.0-beta.13",
"@mui/core-downloads-tracker": "^5.14.5", "@mui/core-downloads-tracker": "^5.14.7",
"@mui/system": "^5.14.5", "@mui/system": "^5.14.7",
"@mui/types": "^7.2.4", "@mui/types": "^7.2.4",
"@mui/utils": "^5.14.5", "@mui/utils": "^5.14.7",
"@types/react-transition-group": "^4.4.6", "@types/react-transition-group": "^4.4.6",
"clsx": "^2.0.0", "clsx": "^2.0.0",
"csstype": "^3.1.2", "csstype": "^3.1.2",
@ -3210,12 +3250,12 @@
} }
}, },
"node_modules/@mui/private-theming": { "node_modules/@mui/private-theming": {
"version": "5.14.5", "version": "5.14.7",
"resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.5.tgz", "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.7.tgz",
"integrity": "sha512-cC4C5RrpXpDaaZyH9QwmPhRLgz+f2SYbOty3cPkk4qPSOSfif2ZEcDD9HTENKDDd9deB+xkPKzzZhi8cxIx8Ig==", "integrity": "sha512-Y86+hmDnJab2Ka42PgxKpK3oL7EiacbeeX3X/lG9LGO0wSc45wZjHeTfIlVSkkUCkexiMKEJp5NlSjZhr27NRQ==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.22.6", "@babel/runtime": "^7.22.10",
"@mui/utils": "^5.14.5", "@mui/utils": "^5.14.7",
"prop-types": "^15.8.1" "prop-types": "^15.8.1"
}, },
"engines": { "engines": {
@ -3236,11 +3276,11 @@
} }
}, },
"node_modules/@mui/styled-engine": { "node_modules/@mui/styled-engine": {
"version": "5.13.2", "version": "5.14.7",
"resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.13.2.tgz", "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.7.tgz",
"integrity": "sha512-VCYCU6xVtXOrIN8lcbuPmoG+u7FYuOERG++fpY74hPpEWkyFQG97F+/XfTQVYzlR2m7nPjnwVUgATcTCMEaMvw==", "integrity": "sha512-hKBETEDsIAkL8/mBwPiQj/vw28OeIhMXC3Tvj4J2bb9snxAKpiZioR1PwqP+6P41twsC/GKBd0Vr9oaWYaHuMg==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.21.0", "@babel/runtime": "^7.22.10",
"@emotion/cache": "^11.11.0", "@emotion/cache": "^11.11.0",
"csstype": "^3.1.2", "csstype": "^3.1.2",
"prop-types": "^15.8.1" "prop-types": "^15.8.1"
@ -3267,15 +3307,15 @@
} }
}, },
"node_modules/@mui/system": { "node_modules/@mui/system": {
"version": "5.14.5", "version": "5.14.7",
"resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.5.tgz", "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.7.tgz",
"integrity": "sha512-mextXZHDeGcR7E1kx43TRARrVXy+gI4wzpUgNv7MqZs1dvTVXQGVeAT6ydj9d6FUqHBPMNLGV/21vJOrpqsL+w==", "integrity": "sha512-jeZtHglc+Pi6qjGoopT6O4RqYXVBMqHVOsjMGP0hxGSSPm1T4gsAu7jU8eqGx9YwwjvvJ0eotTjFqw7iJ6qE2Q==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.22.6", "@babel/runtime": "^7.22.10",
"@mui/private-theming": "^5.14.5", "@mui/private-theming": "^5.14.7",
"@mui/styled-engine": "^5.13.2", "@mui/styled-engine": "^5.14.7",
"@mui/types": "^7.2.4", "@mui/types": "^7.2.4",
"@mui/utils": "^5.14.5", "@mui/utils": "^5.14.7",
"clsx": "^2.0.0", "clsx": "^2.0.0",
"csstype": "^3.1.2", "csstype": "^3.1.2",
"prop-types": "^15.8.1" "prop-types": "^15.8.1"
@ -3327,11 +3367,11 @@
} }
}, },
"node_modules/@mui/utils": { "node_modules/@mui/utils": {
"version": "5.14.5", "version": "5.14.7",
"resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.5.tgz", "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.7.tgz",
"integrity": "sha512-6Hzw63VR9C5xYv+CbjndoRLU6Gntal8rJ5W+GUzkyHrGWIyYPWZPa6AevnyGioySNETATe1H9oXS8f/7qgIHJA==", "integrity": "sha512-RtheP/aBoPogVdi8vj8Vo2IFnRa4mZVmnD0RGlVZ49yF60rZs+xP4/KbpIrTr83xVs34QmHQ2aQ+IX7I0a0dDw==",
"dependencies": { "dependencies": {
"@babel/runtime": "^7.22.6", "@babel/runtime": "^7.22.10",
"@types/prop-types": "^15.7.5", "@types/prop-types": "^15.7.5",
"@types/react-is": "^18.2.1", "@types/react-is": "^18.2.1",
"prop-types": "^15.8.1", "prop-types": "^15.8.1",
@ -4144,9 +4184,9 @@
"integrity": "sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw==" "integrity": "sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw=="
}, },
"node_modules/@types/node": { "node_modules/@types/node": {
"version": "16.18.38", "version": "16.18.46",
"resolved": "https://registry.npmjs.org/@types/node/-/node-16.18.38.tgz", "resolved": "https://registry.npmjs.org/@types/node/-/node-16.18.46.tgz",
"integrity": "sha512-6sfo1qTulpVbkxECP+AVrHV9OoJqhzCsfTNp5NIG+enM4HyM3HvZCO798WShIXBN0+QtDIcutJCjsVYnQP5rIQ==" "integrity": "sha512-Mnq3O9Xz52exs3mlxMcQuA7/9VFe/dXcrgAyfjLkABIqxXKOgBRjyazTxUbjsxDa4BP7hhPliyjVTP9RDP14xg=="
}, },
"node_modules/@types/parse-json": { "node_modules/@types/parse-json": {
"version": "4.0.0", "version": "4.0.0",

View File

@ -25,6 +25,7 @@ import { MemberInput } from "../../widgets/forms/MemberInput";
import { PropSelect } from "../../widgets/forms/PropSelect"; import { PropSelect } from "../../widgets/forms/PropSelect";
import { UploadPhotoButton } from "../../widgets/forms/UploadPhotoButton"; import { UploadPhotoButton } from "../../widgets/forms/UploadPhotoButton";
import { useQuery } from "../../hooks/useQuery"; import { useQuery } from "../../hooks/useQuery";
import { useLoadingMessage } from "../../hooks/context_providers/LoadingMessageProvider";
/** /**
* Create a new couple route * Create a new couple route
@ -165,7 +166,8 @@ export function FamilyEditCoupleRoute(): React.ReactElement {
const cancel = () => { const cancel = () => {
setShouldQuit(true); setShouldQuit(true);
n(-1); n(family.family.coupleURL(couple!));
//n(-1);
}; };
const save = async (c: Couple) => { const save = async (c: Couple) => {
@ -210,13 +212,14 @@ export function CouplePage(p: {
shouldAllowLeaving?: boolean; shouldAllowLeaving?: boolean;
children?: Member[]; children?: Member[];
onCancel?: () => void; onCancel?: () => void;
onSave?: (m: Couple) => void; onSave?: (m: Couple) => Promise<void>;
onRequestEdit?: () => void; onRequestEdit?: () => void;
onRequestDelete?: () => void; onRequestDelete?: () => void;
onForceReload?: () => void; onForceReload?: () => void;
}): React.ReactElement { }): React.ReactElement {
const confirm = useConfirm(); const confirm = useConfirm();
const snackbar = useSnackbar(); const snackbar = useSnackbar();
const loadingMessage = useLoadingMessage();
const family = useFamily(); const family = useFamily();
@ -230,8 +233,12 @@ export function CouplePage(p: {
setCouple(new Couple(structuredClone(couple))); setCouple(new Couple(structuredClone(couple)));
}; };
const save = () => { const save = async () => {
p.onSave!(couple); loadingMessage.show(
"Enregistrement des informations du couple en cours..."
);
await p.onSave!(couple);
loadingMessage.hide();
}; };
const cancel = async () => { const cancel = async () => {

View File

@ -39,6 +39,7 @@ import { UploadPhotoButton } from "../../widgets/forms/UploadPhotoButton";
import { useQuery } from "../../hooks/useQuery"; import { useQuery } from "../../hooks/useQuery";
import { mdiFamilyTree } from "@mdi/js"; import { mdiFamilyTree } from "@mdi/js";
import Icon from "@mdi/react"; import Icon from "@mdi/react";
import { useLoadingMessage } from "../../hooks/context_providers/LoadingMessageProvider";
/** /**
* Create a new member route * Create a new member route
@ -185,8 +186,8 @@ export function FamilyEditMemberRoute(): React.ReactElement {
const cancel = () => { const cancel = () => {
setShouldQuit(true); setShouldQuit(true);
//n(family.family.URL(`member/${member!.id}`)); n(family.family.memberURL(member!));
n(-1); //n(-1);
}; };
const save = async (m: Member) => { const save = async (m: Member) => {
@ -233,7 +234,7 @@ export function MemberPage(p: {
siblings?: Member[]; siblings?: Member[];
couples?: Couple[]; couples?: Couple[];
onCancel?: () => void; onCancel?: () => void;
onSave?: (m: Member) => void; onSave?: (m: Member) => Promise<void>;
onRequestEdit?: () => void; onRequestEdit?: () => void;
onRequestDelete?: () => void; onRequestDelete?: () => void;
onForceReload?: () => void; onForceReload?: () => void;
@ -241,6 +242,7 @@ export function MemberPage(p: {
}): React.ReactElement { }): React.ReactElement {
const confirm = useConfirm(); const confirm = useConfirm();
const snackbar = useSnackbar(); const snackbar = useSnackbar();
const loadingMessage = useLoadingMessage();
const family = useFamily(); const family = useFamily();
@ -254,8 +256,12 @@ export function MemberPage(p: {
setMember(new Member(structuredClone(member))); setMember(new Member(structuredClone(member)));
}; };
const save = () => { const save = async () => {
p.onSave!(member); loadingMessage.show(
"Enregistrement des informations du membre en cours..."
);
await p.onSave!(member);
loadingMessage.hide();
}; };
const cancel = async () => { const cancel = async () => {

View File

@ -4,7 +4,7 @@ import EditIcon from "@mui/icons-material/Edit";
import FemaleIcon from "@mui/icons-material/Female"; import FemaleIcon from "@mui/icons-material/Female";
import MaleIcon from "@mui/icons-material/Male"; import MaleIcon from "@mui/icons-material/Male";
import VisibilityIcon from "@mui/icons-material/Visibility"; import VisibilityIcon from "@mui/icons-material/Visibility";
import { Button, TextField, Tooltip } from "@mui/material"; import { Button, TextField, Tooltip, Typography } from "@mui/material";
import { DataGrid, GridActionsCellItem, GridColDef } from "@mui/x-data-grid"; import { DataGrid, GridActionsCellItem, GridColDef } from "@mui/x-data-grid";
import React from "react"; import React from "react";
import { useNavigate } from "react-router-dom"; import { useNavigate } from "react-router-dom";
@ -165,7 +165,8 @@ function MembersTable(p: {
headerName: "Père", headerName: "Père",
flex: 5, flex: 5,
renderCell(params) { renderCell(params) {
if (!params.row.father) return <></>; if (!params.row.father)
return <Typography color="red">Non renseigné</Typography>;
return family.members.get(params.row.father)!.fullName; return family.members.get(params.row.father)!.fullName;
}, },
}, },
@ -174,7 +175,8 @@ function MembersTable(p: {
headerName: "Mère", headerName: "Mère",
flex: 5, flex: 5,
renderCell(params) { renderCell(params) {
if (!params.row.mother) return <></>; if (!params.row.mother)
return <Typography color="red">Non renseignée</Typography>;
return family.members.get(params.row.mother)!.fullName; return family.members.get(params.row.mother)!.fullName;
}, },
}, },

View File

@ -254,6 +254,7 @@ function NodeArea(p: {
let pers2 = p.node.spouse?.member; let pers2 = p.node.spouse?.member;
let didSwap = false; let didSwap = false;
// Show male of the left (all the time)
if (pers2?.sex === "M") { if (pers2?.sex === "M") {
let s = pers1; let s = pers1;
pers1 = pers2; pers1 = pers2;
@ -293,10 +294,37 @@ function NodeArea(p: {
let childrenLinkX: number; let childrenLinkX: number;
let childrenLinkY: number; let childrenLinkY: number;
if (p.node.spouse) { // If the father is the father of all the children, while the
// mother is not the mother of any of the children
if (
pers2 &&
p.node.down.every(
(n) => n.member.father === pers1.id && n.member.mother !== pers2!.id
)
) {
childrenLinkX = parent_x_offset + Math.floor(memberCardWidth(pers1) / 2);
childrenLinkY = p.y + CARD_HEIGHT + 2;
}
// If the mother is the mother of all the children, while the
// father is not the father of any of the children
else if (
pers2 &&
p.node.down.every(
(n) => n.member.father !== pers1.id && n.member.mother === pers2!.id
)
) {
childrenLinkX = beginSecondFaceX! + Math.floor(memberCardWidth(pers2) / 2);
childrenLinkY = p.y + CARD_HEIGHT + 2;
}
// Normal couple
else if (p.node.spouse) {
childrenLinkX = Math.floor((endFirstFaceX + beginSecondFaceX!) / 2); childrenLinkX = Math.floor((endFirstFaceX + beginSecondFaceX!) / 2);
childrenLinkY = middleParentFaceY; childrenLinkY = middleParentFaceY;
} else { }
// Single person
else {
childrenLinkX = parent_x_offset + Math.floor(memberCardWidth(pers1) / 2); childrenLinkX = parent_x_offset + Math.floor(memberCardWidth(pers1) / 2);
childrenLinkY = p.y + CARD_HEIGHT + 2; childrenLinkY = p.y + CARD_HEIGHT + 2;
} }

View File

@ -85,9 +85,9 @@ dependencies = [
[[package]] [[package]]
name = "actix-multipart" name = "actix-multipart"
version = "0.6.0" version = "0.6.1"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dee489e3c01eae4d1c35b03c4493f71cb40d93f66b14558feb1b1a807671cc4e" checksum = "3b960e2aea75f49c8f069108063d12a48d329fc8b60b786dfc7552a9d5918d2d"
dependencies = [ dependencies = [
"actix-multipart-derive", "actix-multipart-derive",
"actix-utils", "actix-utils",
@ -110,15 +110,15 @@ dependencies = [
[[package]] [[package]]
name = "actix-multipart-derive" name = "actix-multipart-derive"
version = "0.6.0" version = "0.6.1"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2ec592f234db8a253cf80531246a4407c8a70530423eea80688a6c5a44a110e7" checksum = "0a0a77f836d869f700e5b47ac7c3c8b9c8bc82e4aec861954c6198abee3ebd4d"
dependencies = [ dependencies = [
"darling 0.14.4", "darling",
"parse-size", "parse-size",
"proc-macro2", "proc-macro2",
"quote", "quote",
"syn 1.0.109", "syn 2.0.29",
] ]
[[package]] [[package]]
@ -849,38 +849,14 @@ dependencies = [
"memchr", "memchr",
] ]
[[package]]
name = "darling"
version = "0.14.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7b750cb3417fd1b327431a470f388520309479ab0bf5e323505daf0290cd3850"
dependencies = [
"darling_core 0.14.4",
"darling_macro 0.14.4",
]
[[package]] [[package]]
name = "darling" name = "darling"
version = "0.20.3" version = "0.20.3"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0209d94da627ab5605dcccf08bb18afa5009cfbef48d8a8b7d7bdbc79be25c5e" checksum = "0209d94da627ab5605dcccf08bb18afa5009cfbef48d8a8b7d7bdbc79be25c5e"
dependencies = [ dependencies = [
"darling_core 0.20.3", "darling_core",
"darling_macro 0.20.3", "darling_macro",
]
[[package]]
name = "darling_core"
version = "0.14.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "109c1ca6e6b7f82cc233a97004ea8ed7ca123a9af07a8230878fcfda9b158bf0"
dependencies = [
"fnv",
"ident_case",
"proc-macro2",
"quote",
"strsim",
"syn 1.0.109",
] ]
[[package]] [[package]]
@ -897,24 +873,13 @@ dependencies = [
"syn 2.0.29", "syn 2.0.29",
] ]
[[package]]
name = "darling_macro"
version = "0.14.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a4aab4dbc9f7611d8b55048a3a16d2d010c2c8334e46304b40ac1cc14bf3b48e"
dependencies = [
"darling_core 0.14.4",
"quote",
"syn 1.0.109",
]
[[package]] [[package]]
name = "darling_macro" name = "darling_macro"
version = "0.20.3" version = "0.20.3"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "836a9bbc7ad63342d6d6e7b815ccab164bc77a2d95d84bc3117a8c0d5c98e2d5" checksum = "836a9bbc7ad63342d6d6e7b815ccab164bc77a2d95d84bc3117a8c0d5c98e2d5"
dependencies = [ dependencies = [
"darling_core 0.20.3", "darling_core",
"quote", "quote",
"syn 2.0.29", "syn 2.0.29",
] ]
@ -2292,9 +2257,9 @@ dependencies = [
[[package]] [[package]]
name = "redis" name = "redis"
version = "0.23.2" version = "0.23.3"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ffd6543a7bc6428396845f6854ccf3d1ae8823816592e2cbe74f20f50f209d02" checksum = "4f49cdc0bb3f412bf8e7d1bd90fe1d9eb10bc5c399ba90973c14662a27b3f8ba"
dependencies = [ dependencies = [
"combine", "combine",
"itoa", "itoa",
@ -2620,7 +2585,7 @@ version = "3.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ea3cee93715c2e266b9338b7544da68a9f24e227722ba482bd1c024367c77c65" checksum = "ea3cee93715c2e266b9338b7544da68a9f24e227722ba482bd1c024367c77c65"
dependencies = [ dependencies = [
"darling 0.20.3", "darling",
"proc-macro2", "proc-macro2",
"quote", "quote",
"syn 2.0.29", "syn 2.0.29",
@ -2795,18 +2760,18 @@ dependencies = [
[[package]] [[package]]
name = "thiserror" name = "thiserror"
version = "1.0.47" version = "1.0.48"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "97a802ec30afc17eee47b2855fc72e0c4cd62be9b4efe6591edde0ec5bd68d8f" checksum = "9d6d7a740b8a666a7e828dd00da9c0dc290dff53154ea77ac109281de90589b7"
dependencies = [ dependencies = [
"thiserror-impl", "thiserror-impl",
] ]
[[package]] [[package]]
name = "thiserror-impl" name = "thiserror-impl"
version = "1.0.47" version = "1.0.48"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6bb623b56e39ab7dcd4b1b98bb6c8f8d907ed255b18de254088016b27a8ee19b" checksum = "49922ecae66cc8a249b77e68d1d0623c1b2c514f0060c27cdc68bd62a1219d35"
dependencies = [ dependencies = [
"proc-macro2", "proc-macro2",
"quote", "quote",

View File

@ -13,19 +13,19 @@ lazy_static = "1.4.0"
anyhow = "1.0.75" anyhow = "1.0.75"
actix-web = "4.3.1" actix-web = "4.3.1"
actix-cors = "0.6.4" actix-cors = "0.6.4"
actix-multipart = "0.6.0" actix-multipart = "0.6.1"
actix-remote-ip = "0.1.0" actix-remote-ip = "0.1.0"
futures-util = "0.3.28" futures-util = "0.3.28"
diesel = { version = "2.0.4", features = ["postgres"] } diesel = { version = "2.0.4", features = ["postgres"] }
serde = { version = "1.0.188", features = ["derive"] } serde = { version = "1.0.188", features = ["derive"] }
serde_json = "1.0.96" serde_json = "1.0.96"
mailchecker = "5.0.9" mailchecker = "5.0.9"
redis = "0.23.2" redis = "0.23.3"
lettre = "0.10.4" lettre = "0.10.4"
rand = "0.8.5" rand = "0.8.5"
bcrypt = "0.15.0" bcrypt = "0.15.0"
light-openid = "1.0.1" light-openid = "1.0.1"
thiserror = "1.0.47" thiserror = "1.0.48"
serde_with = "3.1.0" serde_with = "3.1.0"
rust_iso3166 = "0.1.10" rust_iso3166 = "0.1.10"
rust-s3 = "0.33.0" rust-s3 = "0.33.0"

View File

@ -103,8 +103,29 @@ fn check_opt_str_val(
Ok(()) Ok(())
} }
fn trim_opt_val(val: &mut Option<String>) {
if let Some(s) = val {
*val = Some(s.trim().to_string());
}
if val.as_deref() == Some("") {
*val = None;
}
}
impl MemberRequest { impl MemberRequest {
pub async fn to_member(self, member: &mut Member) -> anyhow::Result<()> { pub async fn to_member(mut self, member: &mut Member) -> anyhow::Result<()> {
// Trim values before processing
trim_opt_val(&mut self.first_name);
trim_opt_val(&mut self.last_name);
trim_opt_val(&mut self.birth_last_name);
trim_opt_val(&mut self.email);
trim_opt_val(&mut self.country);
trim_opt_val(&mut self.address);
trim_opt_val(&mut self.city);
trim_opt_val(&mut self.note);
trim_opt_val(&mut self.phone);
let c = StaticConstraints::default(); let c = StaticConstraints::default();
check_opt_str_val( check_opt_str_val(
&self.first_name, &self.first_name,

View File

@ -6,6 +6,7 @@ diesel::table! {
family_id -> Int4, family_id -> Int4,
wife -> Nullable<Int4>, wife -> Nullable<Int4>,
husband -> Nullable<Int4>, husband -> Nullable<Int4>,
#[max_length = 1]
state -> Nullable<Varchar>, state -> Nullable<Varchar>,
photo_id -> Nullable<Int4>, photo_id -> Nullable<Int4>,
time_create -> Int8, time_create -> Int8,
@ -23,7 +24,9 @@ diesel::table! {
families (id) { families (id) {
id -> Int4, id -> Int4,
time_create -> Int8, time_create -> Int8,
#[max_length = 30]
name -> Varchar, name -> Varchar,
#[max_length = 7]
invitation_code -> Varchar, invitation_code -> Varchar,
disable_couple_photos -> Bool, disable_couple_photos -> Bool,
} }
@ -33,16 +36,26 @@ diesel::table! {
members (id) { members (id) {
id -> Int4, id -> Int4,
family_id -> Int4, family_id -> Int4,
#[max_length = 30]
first_name -> Nullable<Varchar>, first_name -> Nullable<Varchar>,
#[max_length = 30]
last_name -> Nullable<Varchar>, last_name -> Nullable<Varchar>,
#[max_length = 30]
birth_last_name -> Nullable<Varchar>, birth_last_name -> Nullable<Varchar>,
photo_id -> Nullable<Int4>, photo_id -> Nullable<Int4>,
#[max_length = 255]
email -> Nullable<Varchar>, email -> Nullable<Varchar>,
#[max_length = 30]
phone -> Nullable<Varchar>, phone -> Nullable<Varchar>,
#[max_length = 155]
address -> Nullable<Varchar>, address -> Nullable<Varchar>,
#[max_length = 150]
city -> Nullable<Varchar>, city -> Nullable<Varchar>,
#[max_length = 12]
postal_code -> Nullable<Varchar>, postal_code -> Nullable<Varchar>,
#[max_length = 2]
country -> Nullable<Varchar>, country -> Nullable<Varchar>,
#[max_length = 1]
sex -> Nullable<Varchar>, sex -> Nullable<Varchar>,
time_create -> Int8, time_create -> Int8,
time_update -> Int8, time_update -> Int8,
@ -71,11 +84,15 @@ diesel::table! {
diesel::table! { diesel::table! {
photos (id) { photos (id) {
id -> Int4, id -> Int4,
#[max_length = 36]
file_id -> Varchar, file_id -> Varchar,
time_create -> Int8, time_create -> Int8,
#[max_length = 150]
mime_type -> Varchar, mime_type -> Varchar,
#[max_length = 130]
sha512 -> Varchar, sha512 -> Varchar,
file_size -> Int4, file_size -> Int4,
#[max_length = 130]
thumb_sha512 -> Varchar, thumb_sha512 -> Varchar,
} }
} }
@ -83,12 +100,16 @@ diesel::table! {
diesel::table! { diesel::table! {
users (id) { users (id) {
id -> Int4, id -> Int4,
#[max_length = 30]
name -> Varchar, name -> Varchar,
#[max_length = 255]
email -> Varchar, email -> Varchar,
password -> Nullable<Varchar>, password -> Nullable<Varchar>,
time_create -> Int8, time_create -> Int8,
#[max_length = 150]
reset_password_token -> Nullable<Varchar>, reset_password_token -> Nullable<Varchar>,
time_gen_reset_token -> Int8, time_gen_reset_token -> Int8,
#[max_length = 150]
delete_account_token -> Nullable<Varchar>, delete_account_token -> Nullable<Varchar>,
time_gen_delete_account_token -> Int8, time_gen_delete_account_token -> Int8,
time_activate -> Int8, time_activate -> Int8,