This commit is contained in:
Kaushik Narayan R 2025-01-10 23:38:47 -07:00
parent f942be8d3f
commit 47eb312ba1
5 changed files with 90 additions and 4 deletions

View File

@ -4,7 +4,6 @@ import { backendDomain } from "./paths";
export const axiosInstance = axios.create({
baseURL: backendDomain,
withCredentials: true,
timeout: 20000,
headers: {
"Content-Type": "application/json",
},

View File

@ -0,0 +1,50 @@
.container {
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
.text {
margin-top: var(--mb-2);
font-family: var(--primaryFont);
font-size: larger;
letter-spacing: 1px;
}
.loader {
width: 80px;
height: 80px;
}
.loader div {
box-sizing: border-box;
display: block;
position: absolute;
width: 64px;
height: 64px;
margin: 8px;
/* border: 7px solid var(--primary); */
border: 7px solid white;
border-radius: 50%;
animation: loader 1.2s cubic-bezier(0.5, 0, 0.5, 1) infinite;
border-color: white transparent transparent transparent;
}
.loader div:nth-child(1) {
animation-delay: -0.45s;
}
.loader div:nth-child(2) {
animation-delay: -0.3s;
}
.loader div:nth-child(3) {
animation-delay: -0.15s;
}
@keyframes loader {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}

View File

@ -0,0 +1,17 @@
import styles from "./SimpleLoader.module.css";
const SimpleLoader = ({ text }: { text?: string }) => {
return (
<div className={`${styles.container}`}>
<div className={`${styles.loader}`}>
<div></div>
<div></div>
<div></div>
<div></div>
</div>
<p className={`${styles.text}`}>{text}</p>
</div>
);
};
export default SimpleLoader;

View File

@ -5,6 +5,10 @@
color: black;
}
.loading {
filter: brightness(70%);
}
.operations_wrapper {
display: flex;
background-color: var(--bgNav);

View File

@ -4,6 +4,7 @@ import {
Controls,
MiniMap,
Background,
Panel,
addEdge,
applyNodeChanges,
applyEdgeChanges,
@ -53,6 +54,7 @@ import {
import { RefreshAuthContext } from "../../App";
import Button from "../../components/Button";
import APIWrapper from "../../components/APIWrapper";
import SimpleLoader from "../../components/SimpleLoader";
const initialNodes: Node[] = [];
const initialEdges: Edge[] = [];
@ -134,6 +136,7 @@ const Graph = () => {
const [selectedEdgeID, setSelectedEdgeID] = useState<Edge["id"]>("");
const [interactive, setInteractive] =
useState<Interactive>(initialInteractive);
const [loading, setLoading] = useState<boolean>(false);
const onFlowInit: OnInit = (_instance) => {
console.debug("flow loaded");
@ -175,6 +178,7 @@ const Graph = () => {
);
// call API to create link
const spotifyPlaylistLinkPrefix = "https://open.spotify.com/playlist/";
setLoading(true);
const resp = await APIWrapper({
apiFn: apiCreateLink,
data: {
@ -183,6 +187,7 @@ const Graph = () => {
},
refreshAuth,
});
setLoading(false);
if (resp?.status === 201) {
showSuccessToastNotification(resp?.data.message);
setLinkEdges((eds) => addEdge(connection, eds));
@ -203,6 +208,7 @@ const Graph = () => {
`deleted connection: ${edges[0].source} -> ${edges[0].target}`
);
// call API to delete link
setLoading(true);
const resp = await APIWrapper({
apiFn: apiDeleteLink,
data: {
@ -211,6 +217,7 @@ const Graph = () => {
},
refreshAuth,
});
setLoading(false);
if (resp?.status === 200) {
showSuccessToastNotification(resp?.data.message);
return { nodes, edges };
@ -228,6 +235,7 @@ const Graph = () => {
}
const selectedEdge = linkEdges.filter((ed) => ed.id === selectedEdgeID)[0];
setLoading(true);
const resp = await APIWrapper({
apiFn: apiBackfillLink,
data: {
@ -236,6 +244,7 @@ const Graph = () => {
},
refreshAuth,
});
setLoading(false);
if (resp?.status === 200) {
showSuccessToastNotification(resp?.data.message);
@ -252,6 +261,7 @@ const Graph = () => {
}
const selectedEdge = linkEdges.filter((ed) => ed.id === selectedEdgeID)[0];
setLoading(true);
const resp = await APIWrapper({
apiFn: apiPruneLink,
data: {
@ -260,6 +270,7 @@ const Graph = () => {
},
refreshAuth,
});
setLoading(false);
if (resp?.status === 200) {
showSuccessToastNotification(resp?.data.message);
@ -359,7 +370,9 @@ const Graph = () => {
);
const fetchGraph = useCallback(async () => {
setLoading(true);
const resp = await APIWrapper({ apiFn: apiFetchGraph, refreshAuth });
setLoading(false);
console.debug(
`graph fetched with ${resp?.data.playlists?.length} nodes and ${resp?.data.links?.length} edges`
);
@ -399,10 +412,12 @@ const Graph = () => {
}, [refreshAuth]);
const updateUserData = async () => {
setLoading(true);
const resp = await APIWrapper({
apiFn: apiUpdateUserData,
refreshAuth,
});
setLoading(false);
showInfoToastNotification(resp?.data.message);
if (resp?.data.removedLinks)
showWarnToastNotification(
@ -442,7 +457,7 @@ const Graph = () => {
};
return (
<div className={styles.graph_wrapper}>
<div className={`${styles.graph_wrapper} ${loading && styles.loading}`}>
<ReactFlow
nodes={playlistNodes}
edges={linkEdges}
@ -452,8 +467,8 @@ const Graph = () => {
proOptions={proOptions}
colorMode={"light"}
fitView
minZoom={0.1}
maxZoom={10}
minZoom={0.05}
maxZoom={20}
elevateEdgesOnSelect
defaultEdgeOptions={edgeOptions}
edgesReconnectable={false}
@ -475,6 +490,7 @@ const Graph = () => {
bgColor={"purple"}
/>
<Background variant={BackgroundVariant.Dots} gap={36} size={3} />
<Panel position="top-right">{loading && <SimpleLoader />}</Panel>
</ReactFlow>
<div className={`${styles.operations_wrapper} custom_scrollbar`}>
<Button onClickMethod={backfillLink}>