Genealogy as a feature #175

Merged
pierre merged 16 commits from genealogy_as_a_feature into master 2024-05-16 19:15:16 +00:00
20 changed files with 67 additions and 62 deletions
Showing only changes of commit cd7462ffb1 - Show all commits

View File

@ -1,6 +1,6 @@
import { APIClient } from "./ApiClient"; import { APIClient } from "./ApiClient";
import { Couple } from "./CoupleApi"; import { Couple } from "./CoupleApi";
import { Member } from "./MemberApi"; import { Member } from "./genealogy/MemberApi";
interface FamilyAPI { interface FamilyAPI {
user_id: number; user_id: number;

View File

@ -1,6 +1,6 @@
import { APIClient } from "./ApiClient"; import { APIClient } from "../ApiClient";
import { DateValue, Member } from "./MemberApi"; import { DateValue, Member } from "./MemberApi";
import { ServerApi } from "./ServerApi"; import { ServerApi } from "../ServerApi";
interface CoupleApiInterface { interface CoupleApiInterface {
id: number; id: number;
@ -161,7 +161,7 @@ export class CoupleApi {
*/ */
static async Create(m: Couple): Promise<Couple> { static async Create(m: Couple): Promise<Couple> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${m.family_id}/couple/create`, uri: `/family/${m.family_id}/genealogy/couple/create`,
method: "POST", method: "POST",
jsonData: m, jsonData: m,
}); });
@ -177,7 +177,7 @@ export class CoupleApi {
couple_id: number couple_id: number
): Promise<Couple> { ): Promise<Couple> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${family_id}/couple/${couple_id}`, uri: `/family/${family_id}/genealogy/couple/${couple_id}`,
method: "GET", method: "GET",
}); });
@ -189,7 +189,7 @@ export class CoupleApi {
*/ */
static async GetEntireList(family_id: number): Promise<CouplesList> { static async GetEntireList(family_id: number): Promise<CouplesList> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${family_id}/couples`, uri: `/family/${family_id}/genealogy/couples`,
method: "GET", method: "GET",
}); });
@ -201,7 +201,7 @@ export class CoupleApi {
*/ */
static async Update(m: Couple): Promise<void> { static async Update(m: Couple): Promise<void> {
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/couple/${m.id}`, uri: `/family/${m.family_id}/genealogy/couple/${m.id}`,
method: "PUT", method: "PUT",
jsonData: m, jsonData: m,
}); });
@ -214,7 +214,7 @@ export class CoupleApi {
const fd = new FormData(); const fd = new FormData();
fd.append("photo", b); fd.append("photo", b);
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/couple/${m.id}/photo`, uri: `/family/${m.family_id}/genealogy/couple/${m.id}/photo`,
method: "PUT", method: "PUT",
formData: fd, formData: fd,
}); });
@ -225,7 +225,7 @@ export class CoupleApi {
*/ */
static async RemoveCouplePhoto(m: Couple): Promise<void> { static async RemoveCouplePhoto(m: Couple): Promise<void> {
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/couple/${m.id}/photo`, uri: `/family/${m.family_id}/genealogy/couple/${m.id}/photo`,
method: "DELETE", method: "DELETE",
}); });
} }
@ -235,7 +235,7 @@ export class CoupleApi {
*/ */
static async Delete(m: Couple): Promise<void> { static async Delete(m: Couple): Promise<void> {
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/couple/${m.id}`, uri: `/family/${m.family_id}/genealogy/couple/${m.id}`,
method: "DELETE", method: "DELETE",
}); });
} }

View File

@ -1,4 +1,4 @@
import { APIClient } from "./ApiClient"; import { APIClient } from "../ApiClient";
/** /**
* Data management api client * Data management api client
@ -9,7 +9,7 @@ export class DataApi {
*/ */
static async ExportData(family_id: number): Promise<Blob> { static async ExportData(family_id: number): Promise<Blob> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${family_id}/data/export`, uri: `/family/${family_id}/genealogy/data/export`,
method: "GET", method: "GET",
}); });
return res.data; return res.data;
@ -22,7 +22,7 @@ export class DataApi {
const fd = new FormData(); const fd = new FormData();
fd.append("archive", archive); fd.append("archive", archive);
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${family_id}/data/import`, uri: `/family/${family_id}/genealogy/data/import`,
method: "PUT", method: "PUT",
formData: fd, formData: fd,
}); });

View File

@ -1,4 +1,4 @@
import { APIClient } from "./ApiClient"; import { APIClient } from "../ApiClient";
import { Couple } from "./CoupleApi"; import { Couple } from "./CoupleApi";
export type Sex = "M" | "F"; export type Sex = "M" | "F";
@ -278,7 +278,7 @@ export class MemberApi {
*/ */
static async Create(m: Member): Promise<Member> { static async Create(m: Member): Promise<Member> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${m.family_id}/member/create`, uri: `/family/${m.family_id}/genealogy/member/create`,
method: "POST", method: "POST",
jsonData: m, jsonData: m,
}); });
@ -294,7 +294,7 @@ export class MemberApi {
member_id: number member_id: number
): Promise<Member> { ): Promise<Member> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${family_id}/member/${member_id}`, uri: `/family/${family_id}/genealogy/member/${member_id}`,
method: "GET", method: "GET",
}); });
@ -306,7 +306,7 @@ export class MemberApi {
*/ */
static async GetEntireList(family_id: number): Promise<MembersList> { static async GetEntireList(family_id: number): Promise<MembersList> {
const res = await APIClient.exec({ const res = await APIClient.exec({
uri: `/family/${family_id}/members`, uri: `/family/${family_id}/genealogy/members`,
method: "GET", method: "GET",
}); });
@ -318,7 +318,7 @@ export class MemberApi {
*/ */
static async Update(m: Member): Promise<void> { static async Update(m: Member): Promise<void> {
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/member/${m.id}`, uri: `/family/${m.family_id}/genealogy/member/${m.id}`,
method: "PUT", method: "PUT",
jsonData: m, jsonData: m,
}); });
@ -331,7 +331,7 @@ export class MemberApi {
const fd = new FormData(); const fd = new FormData();
fd.append("photo", b); fd.append("photo", b);
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/member/${m.id}/photo`, uri: `/family/${m.family_id}/genealogy/member/${m.id}/photo`,
method: "PUT", method: "PUT",
formData: fd, formData: fd,
}); });
@ -342,7 +342,7 @@ export class MemberApi {
*/ */
static async RemoveMemberPhoto(m: Member): Promise<void> { static async RemoveMemberPhoto(m: Member): Promise<void> {
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/member/${m.id}/photo`, uri: `/family/${m.family_id}/genealogy/member/${m.id}/photo`,
method: "DELETE", method: "DELETE",
}); });
} }
@ -352,7 +352,7 @@ export class MemberApi {
*/ */
static async Delete(m: Member): Promise<void> { static async Delete(m: Member): Promise<void> {
await APIClient.exec({ await APIClient.exec({
uri: `/family/${m.family_id}/member/${m.id}`, uri: `/family/${m.family_id}/genealogy/member/${m.id}`,
method: "DELETE", method: "DELETE",
}); });
} }

View File

@ -6,8 +6,8 @@ import SaveIcon from "@mui/icons-material/Save";
import { Button, Grid, Stack } from "@mui/material"; import { Button, Grid, Stack } from "@mui/material";
import React from "react"; import React from "react";
import { useNavigate, useParams } from "react-router-dom"; import { useNavigate, useParams } from "react-router-dom";
import { Couple, CoupleApi } from "../../api/CoupleApi"; import { Couple, CoupleApi } from "../../api/genealogy/CoupleApi";
import { Member } from "../../api/MemberApi"; import { Member } from "../../api/genealogy/MemberApi";
import { ServerApi } from "../../api/ServerApi"; import { ServerApi } from "../../api/ServerApi";
import { useAlert } from "../../hooks/context_providers/AlertDialogProvider"; import { useAlert } from "../../hooks/context_providers/AlertDialogProvider";
import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider"; import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider";

View File

@ -6,8 +6,8 @@ import { Button, TextField, Tooltip } 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";
import { Couple, CoupleApi } from "../../api/CoupleApi"; import { Couple, CoupleApi } from "../../api/genealogy/CoupleApi";
import { dateTimestamp, fmtDate } from "../../api/MemberApi"; import { dateTimestamp, fmtDate } from "../../api/genealogy/MemberApi";
import { ServerApi } from "../../api/ServerApi"; import { ServerApi } from "../../api/ServerApi";
import { useAlert } from "../../hooks/context_providers/AlertDialogProvider"; import { useAlert } from "../../hooks/context_providers/AlertDialogProvider";
import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider"; import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider";

View File

@ -14,8 +14,8 @@ import {
import * as EmailValidator from "email-validator"; import * as EmailValidator from "email-validator";
import React from "react"; import React from "react";
import { useNavigate, useParams } from "react-router-dom"; import { useNavigate, useParams } from "react-router-dom";
import { Couple } from "../../api/CoupleApi"; import { Couple } from "../../api/genealogy/CoupleApi";
import { Member, MemberApi, fmtDate } from "../../api/MemberApi"; import { Member, MemberApi, fmtDate } from "../../api/genealogy/MemberApi";
import { ServerApi } from "../../api/ServerApi"; import { ServerApi } from "../../api/ServerApi";
import { useAlert } from "../../hooks/context_providers/AlertDialogProvider"; import { useAlert } from "../../hooks/context_providers/AlertDialogProvider";
import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider"; import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider";

View File

@ -8,7 +8,12 @@ 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";
import { Member, MemberApi, dateTimestamp, fmtDate } from "../../api/MemberApi"; import {
Member,
MemberApi,
dateTimestamp,
fmtDate,
} from "../../api/genealogy/MemberApi";
import { useAlert } from "../../hooks/context_providers/AlertDialogProvider"; import { useAlert } from "../../hooks/context_providers/AlertDialogProvider";
import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider"; import { useConfirm } from "../../hooks/context_providers/ConfirmDialogProvider";
import { useSnackbar } from "../../hooks/context_providers/SnackbarProvider"; import { useSnackbar } from "../../hooks/context_providers/SnackbarProvider";

View File

@ -14,7 +14,7 @@ import {
} from "@mui/material"; } from "@mui/material";
import React from "react"; import React from "react";
import { useNavigate } from "react-router-dom"; import { useNavigate } from "react-router-dom";
import { DataApi } from "../../api/DataApi"; import { DataApi } from "../../api/genealogy/DataApi";
import { FamilyApi } from "../../api/FamilyApi"; import { FamilyApi } from "../../api/FamilyApi";
import { ServerApi } from "../../api/ServerApi"; import { ServerApi } from "../../api/ServerApi";
import { useAlert } from "../../hooks/context_providers/AlertDialogProvider"; import { useAlert } from "../../hooks/context_providers/AlertDialogProvider";

View File

@ -1,5 +1,5 @@
import { Couple, CouplesList } from "../api/CoupleApi"; import { Couple, CouplesList } from "../api/genealogy/CoupleApi";
import { Member, MembersList, dateTimestamp } from "../api/MemberApi"; import { Member, MembersList, dateTimestamp } from "../api/genealogy/MemberApi";
export interface CoupleInformation { export interface CoupleInformation {
couple: Couple; couple: Couple;

View File

@ -26,9 +26,9 @@ import {
} from "@mui/material"; } from "@mui/material";
import React from "react"; import React from "react";
import { Outlet, useLocation, useParams } from "react-router-dom"; import { Outlet, useLocation, useParams } from "react-router-dom";
import { CoupleApi, CouplesList } from "../api/CoupleApi"; import { CoupleApi, CouplesList } from "../api/genealogy/CoupleApi";
import { ExtendedFamilyInfo, FamilyApi } from "../api/FamilyApi"; import { ExtendedFamilyInfo, FamilyApi } from "../api/FamilyApi";
import { MemberApi, MembersList } from "../api/MemberApi"; import { MemberApi, MembersList } from "../api/genealogy/MemberApi";
import { useAlert } from "../hooks/context_providers/AlertDialogProvider"; import { useAlert } from "../hooks/context_providers/AlertDialogProvider";
import { useConfirm } from "../hooks/context_providers/ConfirmDialogProvider"; import { useConfirm } from "../hooks/context_providers/ConfirmDialogProvider";
import { useSnackbar } from "../hooks/context_providers/SnackbarProvider"; import { useSnackbar } from "../hooks/context_providers/SnackbarProvider";

View File

@ -5,8 +5,8 @@ import ExpandMoreIcon from "@mui/icons-material/ExpandMore";
import { TreeItem, SimpleTreeView } from "@mui/x-tree-view"; import { TreeItem, SimpleTreeView } from "@mui/x-tree-view";
import React from "react"; import React from "react";
import { useNavigate } from "react-router-dom"; import { useNavigate } from "react-router-dom";
import { Couple } from "../api/CoupleApi"; import { Couple } from "../api/genealogy/CoupleApi";
import { Member, fmtDate } from "../api/MemberApi"; import { Member, fmtDate } from "../api/genealogy/MemberApi";
import { FamilyTreeNode } from "../utils/family_tree"; import { FamilyTreeNode } from "../utils/family_tree";
import { useFamily } from "./BaseFamilyRoute"; import { useFamily } from "./BaseFamilyRoute";
import { MemberPhoto } from "./MemberPhoto"; import { MemberPhoto } from "./MemberPhoto";

View File

@ -1,5 +1,5 @@
import { Avatar } from "@mui/material"; import { Avatar } from "@mui/material";
import { Couple } from "../api/CoupleApi"; import { Couple } from "../api/genealogy/CoupleApi";
export function CouplePhoto(p: { export function CouplePhoto(p: {
couple: Couple; couple: Couple;

View File

@ -5,7 +5,7 @@ import {
ListItemSecondaryAction, ListItemSecondaryAction,
ListItemText, ListItemText,
} from "@mui/material"; } from "@mui/material";
import { Member, fmtDate } from "../api/MemberApi"; import { Member, fmtDate } from "../api/genealogy/MemberApi";
import { MemberPhoto } from "./MemberPhoto"; import { MemberPhoto } from "./MemberPhoto";
import Icon from "@mdi/react"; import Icon from "@mdi/react";
import FemaleIcon from "@mui/icons-material/Female"; import FemaleIcon from "@mui/icons-material/Female";

View File

@ -1,5 +1,5 @@
import { Avatar } from "@mui/material"; import { Avatar } from "@mui/material";
import { Member } from "../api/MemberApi"; import { Member } from "../api/genealogy/MemberApi";
export function MemberPhoto(p: { export function MemberPhoto(p: {
member?: Member; member?: Member;

View File

@ -1,6 +1,6 @@
import { Stack, TextField, Typography } from "@mui/material"; import { Stack, TextField, Typography } from "@mui/material";
import { NumberConstraint, ServerApi } from "../../api/ServerApi"; import { NumberConstraint, ServerApi } from "../../api/ServerApi";
import { DateValue, fmtDate } from "../../api/MemberApi"; import { DateValue, fmtDate } from "../../api/genealogy/MemberApi";
import { PropEdit } from "./PropEdit"; import { PropEdit } from "./PropEdit";
export function DateInput(p: { export function DateInput(p: {

View File

@ -2,7 +2,7 @@ import ClearIcon from "@mui/icons-material/Clear";
import { Autocomplete, IconButton, TextField, Typography } from "@mui/material"; import { Autocomplete, IconButton, TextField, Typography } from "@mui/material";
import React from "react"; import React from "react";
import { useNavigate } from "react-router-dom"; import { useNavigate } from "react-router-dom";
import { Member } from "../../api/MemberApi"; import { Member } from "../../api/genealogy/MemberApi";
import { useFamily } from "../BaseFamilyRoute"; import { useFamily } from "../BaseFamilyRoute";
import { MemberItem } from "../MemberItem"; import { MemberItem } from "../MemberItem";

View File

@ -6,7 +6,7 @@ import {
Radio, Radio,
Typography, Typography,
} from "@mui/material"; } from "@mui/material";
import { Sex } from "../../api/MemberApi"; import { Sex } from "../../api/genealogy/MemberApi";
export function SexSelection(p: { export function SexSelection(p: {
readonly?: boolean; readonly?: boolean;

View File

@ -5,8 +5,8 @@ import { IconButton, Tooltip } from "@mui/material";
import jsPDF from "jspdf"; import jsPDF from "jspdf";
import React from "react"; import React from "react";
import { TransformComponent, TransformWrapper } from "react-zoom-pan-pinch"; import { TransformComponent, TransformWrapper } from "react-zoom-pan-pinch";
import { Couple } from "../../api/CoupleApi"; import { Couple } from "../../api/genealogy/CoupleApi";
import { Member } from "../../api/MemberApi"; import { Member } from "../../api/genealogy/MemberApi";
import { useDarkTheme } from "../../hooks/context_providers/DarkThemeProvider"; import { useDarkTheme } from "../../hooks/context_providers/DarkThemeProvider";
import { FamilyTreeNode } from "../../utils/family_tree"; import { FamilyTreeNode } from "../../utils/family_tree";
import { downloadBlob } from "../../utils/files_utils"; import { downloadBlob } from "../../utils/files_utils";

View File

@ -137,71 +137,71 @@ async fn main() -> std::io::Result<()> {
"/family/{id}/user/{user_id}", "/family/{id}/user/{user_id}",
web::delete().to(families_controller::delete_membership), web::delete().to(families_controller::delete_membership),
) )
// Members controller // [GENEALOGY] Members controller
.route( .route(
"/family/{id}/member/create", "/family/{id}/genealogy/member/create",
web::post().to(members_controller::create), web::post().to(members_controller::create),
) )
.route( .route(
"/family/{id}/members", "/family/{id}/genealogy/members",
web::get().to(members_controller::get_all), web::get().to(members_controller::get_all),
) )
.route( .route(
"/family/{id}/member/{member_id}", "/family/{id}/genealogy/member/{member_id}",
web::get().to(members_controller::get_single), web::get().to(members_controller::get_single),
) )
.route( .route(
"/family/{id}/member/{member_id}", "/family/{id}/genealogy/member/{member_id}",
web::put().to(members_controller::update), web::put().to(members_controller::update),
) )
.route( .route(
"/family/{id}/member/{member_id}", "/family/{id}/genealogy/member/{member_id}",
web::delete().to(members_controller::delete), web::delete().to(members_controller::delete),
) )
.route( .route(
"/family/{id}/member/{member_id}/photo", "/family/{id}/genealogy/member/{member_id}/photo",
web::put().to(members_controller::set_photo), web::put().to(members_controller::set_photo),
) )
.route( .route(
"/family/{id}/member/{member_id}/photo", "/family/{id}/genealogy/member/{member_id}/photo",
web::delete().to(members_controller::remove_photo), web::delete().to(members_controller::remove_photo),
) )
// Couples controller // [GENEALOGY] Couples controller
.route( .route(
"/family/{id}/couple/create", "/family/{id}/genealogy/couple/create",
web::post().to(couples_controller::create), web::post().to(couples_controller::create),
) )
.route( .route(
"/family/{id}/couples", "/family/{id}/genealogy/couples",
web::get().to(couples_controller::get_all), web::get().to(couples_controller::get_all),
) )
.route( .route(
"/family/{id}/couple/{couple_id}", "/family/{id}/genealogy/couple/{couple_id}",
web::get().to(couples_controller::get_single), web::get().to(couples_controller::get_single),
) )
.route( .route(
"/family/{id}/couple/{couple_id}", "/family/{id}/genealogy/couple/{couple_id}",
web::put().to(couples_controller::update), web::put().to(couples_controller::update),
) )
.route( .route(
"/family/{id}/couple/{couple_id}", "/family/{id}/genealogy/couple/{couple_id}",
web::delete().to(couples_controller::delete), web::delete().to(couples_controller::delete),
) )
.route( .route(
"/family/{id}/couple/{couple_id}/photo", "/family/{id}/genealogy/couple/{couple_id}/photo",
web::put().to(couples_controller::set_photo), web::put().to(couples_controller::set_photo),
) )
.route( .route(
"/family/{id}/couple/{couple_id}/photo", "/family/{id}/genealogy/couple/{couple_id}/photo",
web::delete().to(couples_controller::remove_photo), web::delete().to(couples_controller::remove_photo),
) )
// Data controller // [GENEALOGY] Data controller
.route( .route(
"/family/{id}/data/export", "/family/{id}/genealogy/data/export",
web::get().to(data_controller::export_family), web::get().to(data_controller::export_family),
) )
.route( .route(
"/family/{id}/data/import", "/family/{id}/genealogy/data/import",
web::put().to(data_controller::import_family), web::put().to(data_controller::import_family),
) )
// Photos controller // Photos controller