diff --git a/src/music-catalogue-ui/components/addAlbumToCatalogue.js b/src/music-catalogue-ui/components/addAlbumToCatalogue.js
new file mode 100644
index 0000000..2a95334
--- /dev/null
+++ b/src/music-catalogue-ui/components/addAlbumToCatalogue.js
@@ -0,0 +1,27 @@
+import { useCallback } from "react";
+import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
+import { faRecordVinyl } from "@fortawesome/free-solid-svg-icons";
+import { apiSetAlbumWishListFlag, apiFetchAlbumsByArtist } from "@/helpers/api";
+
+const AddAlbumToWishList = ({ artistId, album, logout, setAlbums }) => {
+ /* Callback to move an album from the wish list into the catalogue */
+ const moveAlbumToCatalogue = useCallback(async () => {
+ // Move the album to the catalogue
+ const result = await apiSetAlbumWishListFlag(album, false, logout);
+ if (result) {
+ // Successful, so refresh the album list
+ const fetchedAlbums = await apiFetchAlbumsByArtist(
+ artistId,
+ true,
+ logout
+ );
+ setAlbums(fetchedAlbums);
+ }
+ }, [album, artistId, logout, setAlbums]);
+
+ return (
+
+ );
+};
+
+export default AddAlbumToWishList;
diff --git a/src/music-catalogue-ui/components/addAlbumToWishList.js b/src/music-catalogue-ui/components/addAlbumToWishList.js
new file mode 100644
index 0000000..9143085
--- /dev/null
+++ b/src/music-catalogue-ui/components/addAlbumToWishList.js
@@ -0,0 +1,27 @@
+import { useCallback } from "react";
+import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
+import { faHeartCirclePlus } from "@fortawesome/free-solid-svg-icons";
+import { apiSetAlbumWishListFlag, apiFetchAlbumsByArtist } from "@/helpers/api";
+
+const AddAlbumToWishList = ({ artistId, album, logout, setAlbums }) => {
+ /* Callback to prompt for confirmation and delete an album */
+ const moveAlbumToWishList = useCallback(async () => {
+ // Move the album to the wish list
+ const result = await apiSetAlbumWishListFlag(album, true, logout);
+ if (result) {
+ // Successful, so refresh the album list
+ const fetchedAlbums = await apiFetchAlbumsByArtist(
+ artistId,
+ false,
+ logout
+ );
+ setAlbums(fetchedAlbums);
+ }
+ }, [album, artistId, logout, setAlbums]);
+
+ return (
+
+ );
+};
+
+export default AddAlbumToWishList;
diff --git a/src/music-catalogue-ui/components/albumList.js b/src/music-catalogue-ui/components/albumList.js
index f55dca1..1cd07c5 100644
--- a/src/music-catalogue-ui/components/albumList.js
+++ b/src/music-catalogue-ui/components/albumList.js
@@ -1,7 +1,5 @@
-import { useCallback } from "react";
import useAlbums from "@/hooks/useAlbums";
import AlbumRow from "./albumRow";
-import { apiDeleteAlbum, apiFetchAlbumsByArtist } from "@/helpers/api";
/**
* Component to render the table of all albums by the specified artist
@@ -19,33 +17,10 @@ const AlbumList = ({ artist, isWishList, navigate, logout }) => {
? `Wish List for ${artist.name}`
: `Albums by ${artist.name}`;
- /* Callback to prompt for confirmation and delete an album */
- const confirmDeleteAlbum = useCallback(
- async (e, album) => {
- // Prevent the default action associated with the click event
- e.preventDefault();
-
- // Show a confirmation message and get the user response
- const message = `This will delete the album "${album.title}" - click OK to confirm`;
- const result = confirm(message);
-
- // If they've confirmed the deletion ...
- if (result) {
- // ... delete the album and confirm the API call was successful
- const result = await apiDeleteAlbum(album.id, logout);
- if (result) {
- // Successful, so refresh the album list
- const fetchedAlbums = await apiFetchAlbumsByArtist(
- artist.id,
- isWishList,
- logout
- );
- setAlbums(fetchedAlbums);
- }
- }
- },
- [artist, isWishList, setAlbums, logout]
- );
+ // Callback to pass to child components to set the album list
+ const setAlbumsCallback = (albums) => {
+ setAlbums(albums);
+ };
return (
<>
@@ -60,6 +35,7 @@ const AlbumList = ({ artist, isWishList, navigate, logout }) => {
Genre |
Released |
|
+ |
@@ -71,7 +47,8 @@ const AlbumList = ({ artist, isWishList, navigate, logout }) => {
album={a}
isWishList={isWishList}
navigate={navigate}
- deleteAlbum={confirmDeleteAlbum}
+ logout={logout}
+ setAlbums={setAlbumsCallback}
/>
))}
diff --git a/src/music-catalogue-ui/components/albumRow.js b/src/music-catalogue-ui/components/albumRow.js
index 851fb21..93c1e48 100644
--- a/src/music-catalogue-ui/components/albumRow.js
+++ b/src/music-catalogue-ui/components/albumRow.js
@@ -1,6 +1,7 @@
import pages from "@/helpers/navigation";
-import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
-import { faTrashAlt } from "@fortawesome/free-solid-svg-icons";
+import DeleteAlbum from "./deleteAlbum";
+import AddAlbumToWishList from "./addAlbumToWishList";
+import AddAlbumToCatalogue from "./addAlbumToCatalogue";
/**
* Component to render a row containing the details of a single album
@@ -8,10 +9,18 @@ import { faTrashAlt } from "@fortawesome/free-solid-svg-icons";
* @param {*} album
* @param {*} isWishList
* @param {*} navigate
- * @param {*} deleteAlbum
+ * @param {*} logout
+ * @param {*} setAlbums
* @returns
*/
-const AlbumRow = ({ artist, album, isWishList, navigate, deleteAlbum }) => {
+const AlbumRow = ({
+ artist,
+ album,
+ isWishList,
+ navigate,
+ logout,
+ setAlbums,
+}) => {
return (
navigate(pages.tracks, artist, album, isWishList)}>
@@ -27,11 +36,30 @@ const AlbumRow = ({ artist, album, isWishList, navigate, deleteAlbum }) => {
{album.released}
|
- deleteAlbum(e, album)}
+
|
+
+ {isWishList == false ? (
+
+ ) : (
+
+ )}
+ |
);
};
diff --git a/src/music-catalogue-ui/components/deleteAlbum.js b/src/music-catalogue-ui/components/deleteAlbum.js
new file mode 100644
index 0000000..bfdc5d6
--- /dev/null
+++ b/src/music-catalogue-ui/components/deleteAlbum.js
@@ -0,0 +1,43 @@
+import { useCallback } from "react";
+import { apiDeleteAlbum, apiFetchAlbumsByArtist } from "@/helpers/api";
+import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
+import { faTrashAlt } from "@fortawesome/free-solid-svg-icons";
+
+const DeleteAlbum = ({ album, isWishList, logout, setAlbums }) => {
+ /* Callback to prompt for confirmation and delete an album */
+ const confirmDeleteAlbum = useCallback(
+ async (e, album) => {
+ // Prevent the default action associated with the click event
+ e.preventDefault();
+
+ // Show a confirmation message and get the user response
+ const message = `This will delete the album "${album.title}" - click OK to confirm`;
+ const result = confirm(message);
+
+ // If they've confirmed the deletion ...
+ if (result) {
+ // ... delete the album and confirm the API call was successful
+ const result = await apiDeleteAlbum(album.id, logout);
+ if (result) {
+ // Successful, so refresh the album list
+ const fetchedAlbums = await apiFetchAlbumsByArtist(
+ artist.id,
+ isWishList,
+ logout
+ );
+ setAlbums(fetchedAlbums);
+ }
+ }
+ },
+ [isWishList, logout, setAlbums]
+ );
+
+ return (
+ confirmDeleteAlbum(e, album)}
+ />
+ );
+};
+
+export default DeleteAlbum;
diff --git a/src/music-catalogue-ui/helpers/api.js b/src/music-catalogue-ui/helpers/api.js
index 0bc5da1..604b2fc 100644
--- a/src/music-catalogue-ui/helpers/api.js
+++ b/src/music-catalogue-ui/helpers/api.js
@@ -307,6 +307,41 @@ const apiLookupAlbum = async (artistName, albumTitle, logout) => {
}
};
+/**
+ * Set the wish list flag on an album
+ * @param {*} album
+ * @param {*} wishListFlag
+ * @param {*} logout
+ * @returns
+ */
+const apiSetAlbumWishListFlag = async (album, wishListFlag, logout) => {
+ // Construct the body - the wish list flat needs to be updated before this
+ // and there's no need to send the track information - an empty array will do
+ album.isWishListItem = wishListFlag;
+ album.tracks = [];
+ const body = JSON.stringify(album);
+ console.log(body);
+
+ // Call the API to set the wish list flag for a given album
+ const url = `${config.api.baseUrl}/albums`;
+ const response = await fetch(url, {
+ method: "PUT",
+ headers: apiGetPostHeaders(),
+ body: body,
+ });
+
+ if (response.ok) {
+ // Get the response content as JSON and return it
+ const album = await apiReadResponseData(response);
+ return album;
+ } else if (response.status == 401) {
+ // Unauthorized so the token's likely expired - force a login
+ logout();
+ } else {
+ return null;
+ }
+};
+
/**
* Request an export of the catalogue
* @param {*} fileName
@@ -390,6 +425,7 @@ export {
apiFetchAlbumById,
apiDeleteAlbum,
apiLookupAlbum,
+ apiSetAlbumWishListFlag,
apiRequestExport,
apiJobStatusReport,
};