Index: frontend/src/App.tsx
===================================================================
--- frontend/src/App.tsx	(revision 98992cf92cf1399ea586c26d6dd45842df661773)
+++ frontend/src/App.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -8,59 +8,64 @@
 import Register from "./pages/Register";
 import UserDetailView from "./pages/UserDetailView";
+import MusicalCollection from "./pages/MusicalCollection";
 
 const Layout = () => {
-	return (
-		<div className="flex flex-col min-h-screen">
-			<Nav />
-			<ToastContainer
-				position="top-right"
-				autoClose={2000}
-				hideProgressBar={false}
-				newestOnTop={false}
-				closeOnClick
-				rtl={false}
-				pauseOnFocusLoss
-				draggable
-				pauseOnHover
-				theme="light"
-			/>
-			<main className="grow">
-				<Outlet />
-			</main>
-		</div>
-	);
+  return (
+    <div className="flex flex-col min-h-screen">
+      <Nav />
+      <ToastContainer
+        position="top-right"
+        autoClose={2000}
+        hideProgressBar={false}
+        newestOnTop={false}
+        closeOnClick
+        rtl={false}
+        pauseOnFocusLoss
+        draggable
+        pauseOnHover
+        theme="light"
+      />
+      <main className="grow">
+        <Outlet />
+      </main>
+    </div>
+  );
 };
 
 const router = createBrowserRouter([
-	{
-		path: "",
-		element: <Layout />,
-		children: [
-			{
-				path: "/",
-				element: <LandingPage />,
-			},
-			{
-				path: "/login",
-				element: <Login />,
-			},
-			{
-				path: "/users",
-				element: <AllUsers />,
-			},
-			{
-				path: "/users/:userId",
-				element: <UserDetailView />,
-			},
-			{
-				path: "/register",
-				element: <Register />,
-			},
-		],
-	},
+  {
+    path: "",
+    element: <Layout />,
+    children: [
+      {
+        path: "/",
+        element: <LandingPage />,
+      },
+      {
+        path: "/login",
+        element: <Login />,
+      },
+      {
+        path: "/users",
+        element: <AllUsers />,
+      },
+      {
+        path: "/users/:userId",
+        element: <UserDetailView />,
+      },
+      {
+        path: "/register",
+        element: <Register />,
+      },
+      {
+        path: "/collection/:type/:id",
+        element: <MusicalCollection />,
+      },
+    ],
+  },
 ]);
 
 function App() {
-	return <RouterProvider router={router} />;
+  return <RouterProvider router={router} />;
 }
 
Index: frontend/src/components/userProfile/ArtistView.tsx
===================================================================
--- frontend/src/components/userProfile/ArtistView.tsx	(revision 98992cf92cf1399ea586c26d6dd45842df661773)
+++ frontend/src/components/userProfile/ArtistView.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -37,5 +37,5 @@
                 className="group cursor-pointer"
                 onClick={() =>
-                  navigate(`/musical-entity/${album.musicalEntityId}`)
+                  navigate(`/collection/album/${album.musicalEntityId}`)
                 }
               >
Index: frontend/src/components/userProfile/ListenerView.tsx
===================================================================
--- frontend/src/components/userProfile/ListenerView.tsx	(revision 98992cf92cf1399ea586c26d6dd45842df661773)
+++ frontend/src/components/userProfile/ListenerView.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -31,5 +31,5 @@
                 key={playlist.id}
                 className="group cursor-pointer"
-                onClick={() => navigate(`/playlist/${playlist.id}`)}
+                onClick={() => navigate(`/playlists/${playlist.id}`)}
               >
                 <div className="aspect-square rounded-md overflow-hidden bg-gray-100 mb-2 relative shadow-sm group-hover:shadow-lg transition-all">
Index: frontend/src/components/userProfile/UserListModal.tsx
===================================================================
--- frontend/src/components/userProfile/UserListModal.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
+++ frontend/src/components/userProfile/UserListModal.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -0,0 +1,85 @@
+import { useNavigate } from "react-router-dom";
+import type { BaseNonAdminUser } from "../../utils/types";
+
+interface ModalProps {
+  title: string;
+  users: BaseNonAdminUser[];
+  onClose: () => void;
+  onFollowToggle: (targetId: number) => Promise<void>;
+}
+
+const UserListModal = ({
+  title,
+  users,
+  onClose,
+  onFollowToggle,
+}: ModalProps) => {
+  const navigate = useNavigate();
+  const baseURL = import.meta.env.VITE_API_BASE_URL;
+
+  return (
+    <div className="fixed inset-0 z-50 flex items-center justify-center bg-black/50 backdrop-blur-sm">
+      <div className="bg-white rounded-xl shadow-2xl w-full max-w-md max-h-[70vh] flex flex-col">
+        <div className="p-4 border-b flex justify-between items-center">
+          <h2 className="text-xl font-bold">{title}</h2>
+          <button
+            onClick={onClose}
+            className="text-gray-500 hover:text-black text-2xl"
+          >
+            &times;
+          </button>
+        </div>
+
+        <div className="overflow-y-auto p-4 flex-1">
+          {users.length === 0 ? (
+            <p className="text-center text-gray-500 py-8">No users found.</p>
+          ) : (
+            users.map((u) => (
+              <div
+                key={u.id}
+                className="flex items-center justify-between p-3 hover:bg-gray-50 rounded-lg transition-colors"
+              >
+                <div
+                  className="flex items-center gap-4 cursor-pointer flex-1"
+                  onClick={() => {
+                    onClose();
+                    navigate(`/users/${u.id}`);
+                  }}
+                >
+                  <div className="w-10 h-10 rounded-full bg-blue-100 overflow-hidden shrink-0 flex items-center justify-center">
+                    {u.profilePhoto ? (
+                      <img
+                        src={`${baseURL}/${u.profilePhoto}`}
+                        className="w-full h-full object-cover"
+                        alt=""
+                      />
+                    ) : (
+                      <span className="text-blue-600 font-bold">
+                        {u.fullName.charAt(0)}
+                      </span>
+                    )}
+                  </div>
+                  <p className="font-semibold text-gray-900">{u.fullName}</p>
+                </div>
+
+                <button
+                  onClick={() => onFollowToggle(u.id)}
+                  className={`px-4 py-1 text-sm font-medium rounded-md transition-colors cursor-pointer ${
+                    u.isFollowedByCurrentUser
+                      ? "bg-gray-200 text-gray-700 hover:bg-gray-300"
+                      : "bg-blue-500 text-white hover:bg-blue-600"
+                  }`}
+                >
+                  {u.isFollowedByCurrentUser ? "Unfollow" : "Follow"}
+                </button>
+              </div>
+            ))
+          )}
+        </div>
+      </div>
+      <div className="absolute inset-0 -z-10" onClick={onClose}></div>
+    </div>
+  );
+};
+
+export default UserListModal;
Index: frontend/src/pages/MusicalCollection.tsx
===================================================================
--- frontend/src/pages/MusicalCollection.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
+++ frontend/src/pages/MusicalCollection.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -0,0 +1,176 @@
+import { useEffect, useState } from "react";
+import { useNavigate, useParams } from "react-router-dom";
+import axiosInstance from "../api/axiosInstance";
+
+interface Song {
+  id: number;
+  title: string;
+  genre: string;
+  type: "SONG";
+  releasedBy: string;
+  isLikedByCurrentUser?: boolean;
+}
+
+interface MusicalEntity {
+  id: number;
+  title: string;
+  genre: string;
+  type: string;
+  releasedBy: string;
+  isLikedByCurrentUser?: boolean;
+  songs?: Song[];
+}
+
+const MusicalCollection = () => {
+  const { type, id } = useParams();
+  const navigate = useNavigate();
+  const [collection, setCollection] = useState<MusicalEntity | null>(null);
+  const [isLoading, setIsLoading] = useState(true);
+  const [error, setError] = useState<string | null>(null);
+
+  useEffect(() => {
+    const fetchData = async () => {
+      setIsLoading(true);
+      setError(null);
+      try {
+        const endpoint =
+          type === "album" ? `/albums/${id}` : `/playlists/${id}`;
+        const response = await axiosInstance.get(endpoint);
+        console.log(response.data);
+        setCollection(response.data);
+      } catch (err: any) {
+        setError(err.response?.data?.error || "Failed to load collection");
+      } finally {
+        setIsLoading(false);
+      }
+    };
+    fetchData();
+  }, [id, type]);
+
+  if (isLoading) {
+    return <div className="p-6">Loading...</div>;
+  }
+
+  if (error) {
+    return (
+      <div className="p-6 bg-red-50 border border-red-200 text-red-700 rounded-lg">
+        <h2 className="font-bold">Error</h2>
+        <p>{error}</p>
+      </div>
+    );
+  }
+
+  if (!collection) return null;
+
+  return (
+    <div className="container mx-auto p-6">
+      <button
+        onClick={() => navigate(-1)}
+        className="mb-4 px-4 py-2 bg-blue-500 text-white rounded hover:bg-blue-600 transition-colors duration-200"
+      >
+        ← Back
+      </button>
+
+      <div className="bg-white shadow-lg rounded-lg p-8">
+        <div className="flex items-start gap-6 mb-8">
+          <div className="shrink-0">
+            <div className="w-40 h-40 rounded-lg bg-gradient-to-br from-blue-400 to-purple-500 flex items-center justify-center text-white text-5xl font-bold shadow-lg">
+              {collection.title.charAt(0).toUpperCase()}
+            </div>
+          </div>
+
+          <div className="flex-1">
+            <span className="inline-block px-3 py-1 bg-blue-100 text-blue-800 rounded-full text-sm font-medium mb-2">
+              {collection.type}
+            </span>
+            <h1 className="text-4xl font-bold mb-3">{collection.title}</h1>
+
+            <div className="flex items-center gap-3 text-gray-700 mb-4">
+              <span className="font-semibold">{collection.releasedBy}</span>
+              <span>•</span>
+              <span className="text-gray-600">{collection.genre}</span>
+              {collection.songs && (
+                <>
+                  <span>•</span>
+                  <span className="text-gray-600">
+                    {collection.songs.length} song
+                    {collection.songs.length !== 1 ? "s" : ""}
+                  </span>
+                </>
+              )}
+            </div>
+
+            <button
+              className="flex items-center gap-2 px-4 py-2 bg-gray-100 hover:bg-gray-200 rounded-lg transition-colors duration-200"
+              aria-label={collection.isLikedByCurrentUser ? "Unlike" : "Like"}
+            >
+              <svg
+                className="w-5 h-5"
+                fill={collection.isLikedByCurrentUser ? "#ef4444" : "none"}
+                stroke={collection.isLikedByCurrentUser ? "#ef4444" : "#6b7280"}
+                strokeWidth="2"
+                viewBox="0 0 24 24"
+              >
+                <path d="M20.84 4.61a5.5 5.5 0 0 0-7.78 0L12 5.67l-1.06-1.06a5.5 5.5 0 0 0-7.78 7.78l1.06 1.06L12 21.23l7.78-7.78 1.06-1.06a5.5 5.5 0 0 0 0-7.78z" />
+              </svg>
+              <span className="text-sm font-medium text-gray-700">
+                {collection.isLikedByCurrentUser ? "Liked" : "Like"}
+              </span>
+            </button>
+          </div>
+        </div>
+
+        <div className="border-t pt-6">
+          <h2 className="text-2xl font-bold mb-4 text-gray-800">Songs</h2>
+
+          {collection.songs && collection.songs.length > 0 ? (
+            <div className="space-y-2">
+              {collection.songs.map((song, index) => (
+                <div
+                  key={song.id}
+                  className="flex items-center gap-4 p-3 rounded-lg hover:bg-gray-50 transition-colors duration-150"
+                >
+                  <span className="text-gray-500 font-medium w-8 text-center">
+                    {index + 1}
+                  </span>
+
+                  <div className="flex-1 min-w-0">
+                    <p className="font-semibold text-gray-900 truncate">
+                      {song.title}
+                    </p>
+                    <p className="text-sm text-gray-600 truncate">
+                      {song.releasedBy}
+                    </p>
+                  </div>
+
+                  <span className="text-sm text-gray-600 px-3 py-1 bg-gray-100 rounded-full">
+                    {song.genre}
+                  </span>
+
+                  <button
+                    className="p-2 hover:bg-gray-100 rounded-full transition-colors duration-200"
+                    aria-label={song.isLikedByCurrentUser ? "Unlike" : "Like"}
+                  >
+                    <svg
+                      className="w-5 h-5"
+                      fill={song.isLikedByCurrentUser ? "#ef4444" : "none"}
+                      stroke={song.isLikedByCurrentUser ? "#ef4444" : "#6b7280"}
+                      strokeWidth="2"
+                      viewBox="0 0 24 24"
+                    >
+                      <path d="M20.84 4.61a5.5 5.5 0 0 0-7.78 0L12 5.67l-1.06-1.06a5.5 5.5 0 0 0-7.78 7.78l1.06 1.06L12 21.23l7.78-7.78 1.06-1.06a5.5 5.5 0 0 0 0-7.78z" />
+                    </svg>
+                  </button>
+                </div>
+              ))}
+            </div>
+          ) : (
+            <p className="text-center text-gray-500 py-8">No songs available</p>
+          )}
+        </div>
+      </div>
+    </div>
+  );
+};
+
+export default MusicalCollection;
Index: frontend/src/pages/UserDetailView.tsx
===================================================================
--- frontend/src/pages/UserDetailView.tsx	(revision 98992cf92cf1399ea586c26d6dd45842df661773)
+++ frontend/src/pages/UserDetailView.tsx	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -4,24 +4,17 @@
 import ArtistView from "../components/userProfile/ArtistView";
 import ListenerView from "../components/userProfile/ListenerView";
+import UserListModal from "../components/userProfile/UserListModal";
 import type {
   MusicalEntity,
   Playlist,
   ArtistContribution,
+  BaseNonAdminUser,
 } from "../utils/types";
 
-interface BaseUser {
-  id: number;
-  fullName: string;
-  userType: string;
-  followers: number;
-  following: number;
-  isFollowedByCurrentUser: boolean;
-}
-
-interface Artist extends BaseUser {
+interface Artist extends BaseNonAdminUser {
   userType: "ARTIST";
   contributions: ArtistContribution[];
 }
-interface Listener extends BaseUser {
+interface Listener extends BaseNonAdminUser {
   userType: "LISTENER";
   likedEntities: MusicalEntity[];
@@ -33,8 +26,13 @@
 const UserDetail = () => {
   // user refers to the selected user NOT to the user from context
+  const baseURL = import.meta.env.VITE_API_BASE_URL;
   const { userId } = useParams();
   const navigate = useNavigate();
   const [user, setUser] = useState<UserProfile | null>(null);
   const [error, setError] = useState<string | null>(null);
+  const [showModal, setShowModal] = useState(false);
+  const [modalTitle, setModalTitle] = useState("");
+  const [modalUsers, setModalUsers] = useState<any[]>([]);
+  const [isLoadingModal, setIsLoadingModal] = useState(false);
   const [isFollowing, setIsFollowing] = useState(false);
 
@@ -47,8 +45,61 @@
         `/users/follow/${userId}`,
       );
+      setUser(response.data);
     } catch (err: any) {
       console.error(err.response?.data?.error);
     } finally {
       setIsFollowing(false);
+    }
+  };
+
+  const displayFollowers = async () => {
+    setIsLoadingModal(true);
+    try {
+      const response = await axiosInstance.get(`/users/followers/${userId}`);
+      setModalUsers(response.data);
+      setModalTitle("Followers");
+      setShowModal(true);
+    } catch (err) {
+      console.error("Failed to fetch followers");
+    } finally {
+      setIsLoadingModal(false);
+    }
+  };
+  const displayFollowing = async () => {
+    setIsLoadingModal(true);
+    try {
+      const response = await axiosInstance.get(`/users/following/${userId}`);
+      setModalUsers(response.data);
+      setModalTitle("Following");
+      setShowModal(true);
+    } catch (err) {
+      console.error("Failed to fetch following users");
+    } finally {
+      setIsLoadingModal(false);
+    }
+  };
+
+  const handleFollowInModal = async (targetId: number) => {
+    try {
+      await axiosInstance.post(`/users/follow/${targetId}`);
+      setModalUsers((prevUsers) =>
+        prevUsers.map((u) => {
+          if (u.id === targetId) {
+            const isNowFollowing = !u.isFollowedByCurrentUser;
+            return {
+              ...u,
+              isFollowedByCurrentUser: isNowFollowing,
+            };
+          }
+          return u;
+        }),
+      );
+
+      if (user && user.id === targetId) {
+        const response = await axiosInstance.get(`/users/${targetId}`);
+        setUser(response.data);
+      }
+    } catch (err) {
+      console.error("Failed to toggle follow in modal", err);
     }
   };
@@ -60,5 +111,4 @@
         const response = await axiosInstance.get(`/users/${userId}`);
         console.log(response.data);
-
         setUser(response.data);
       } catch (err: any) {
@@ -84,4 +134,11 @@
   return (
     <div className="container mx-auto p-6">
+      {isLoadingModal && (
+        <div className="fixed inset-0 z-40 bg-black/30 backdrop-blur-sm flex items-center justify-center">
+          <div className="flex items-center gap-3">
+            <div className="w-6 h-6 border-3 border-blue-500 border-t-transparent rounded-full animate-spin"></div>
+          </div>
+        </div>
+      )}
       <button
         onClick={() => navigate(-1)}
@@ -94,6 +151,14 @@
         <div className="flex items-start gap-6 mb-8">
           <div className="shrink-0">
-            <div className="w-32 h-32 rounded-full bg-linear-to-br from-blue-400 to-purple-500 flex items-center justify-center text-white text-4xl font-bold shadow-lg">
-              {user.fullName.charAt(0).toUpperCase()}
+            <div className="w-32 h-32 rounded-full bg-linear-to-br from-blue-400 to-purple-500 flex items-center justify-center text-white text-4xl font-bold shadow-lg overflow-hidden">
+              {user.profilePhoto ? (
+                <img
+                  src={`${baseURL}/${user.profilePhoto}`}
+                  alt={user.fullName}
+                  className="w-full h-full object-cover"
+                />
+              ) : (
+                user.fullName.charAt(0).toUpperCase()
+              )}
             </div>
           </div>
@@ -106,9 +171,19 @@
 
             <div className="flex gap-6 mb-4 text-gray-700">
-              <div className="flex flex-col">
+              <div
+                className={`flex flex-col ${user.userType == "LISTENER" ? "cursor-pointer" : "cursor-default"}`}
+                onClick={
+                  user.userType === "LISTENER" ? displayFollowers : undefined
+                }
+              >
                 <span className="text-2xl font-bold">{user.followers}</span>
                 <span className="text-sm text-gray-500">Followers</span>
               </div>
-              <div className="flex flex-col">
+              <div
+                className={`flex flex-col ${user.userType == "LISTENER" ? "cursor-pointer" : "cursor-default"}`}
+                onClick={
+                  user.userType === "LISTENER" ? displayFollowing : undefined
+                }
+              >
                 <span className="text-2xl font-bold">{user.following}</span>
                 <span className="text-sm text-gray-500">Following</span>
@@ -144,4 +219,13 @@
           />
         )}
+
+        {showModal && (
+          <UserListModal
+            title={modalTitle}
+            users={modalUsers}
+            onClose={() => setShowModal(false)}
+            onFollowToggle={handleFollowInModal}
+          />
+        )}
       </div>
     </div>
Index: frontend/src/utils/types.ts
===================================================================
--- frontend/src/utils/types.ts	(revision 98992cf92cf1399ea586c26d6dd45842df661773)
+++ frontend/src/utils/types.ts	(revision 2b08bed6a1ac91c0de26078bed3ee44d43611bd4)
@@ -19,4 +19,5 @@
   genre: string;
   type: string;
+  releasedBy: string;
 }
 
@@ -27,2 +28,12 @@
   creatorName: string;
 }
+
+export interface BaseNonAdminUser {
+  id: number;
+  fullName: string;
+  userType: string;
+  profilePhoto: string;
+  followers: number;
+  following: number;
+  isFollowedByCurrentUser: boolean;
+}
