73 lines
2 KiB
TypeScript
73 lines
2 KiB
TypeScript
import type { CollectionConfig } from "payload";
|
|
import hasRoles from "@/utils/access-control/hasRoles";
|
|
|
|
function isStaff(user: Parameters<typeof hasRoles>[1]): boolean {
|
|
return hasRoles(["admin", "developer"], user);
|
|
}
|
|
|
|
const STAFF_ROLES = ["admin", "developer"];
|
|
|
|
export const StoryBeatStates: CollectionConfig = {
|
|
slug: "story-beat-states",
|
|
admin: {
|
|
group: "Story",
|
|
useAsTitle: "beat",
|
|
defaultColumns: ["user", "beat", "readAt", "reaction"],
|
|
description: "Per-user read markers and reactions for story beats.",
|
|
// The admin-panel `user` is a client-side user type, so check its roles
|
|
// structurally rather than through hasRoles.
|
|
hidden: ({ user }) =>
|
|
user?.collection !== "users" ||
|
|
!STAFF_ROLES.some((role) => (user.roles ?? []).includes(role)),
|
|
},
|
|
access: {
|
|
// Users can read/update only their own state; staff see everything.
|
|
read: ({ req }) => {
|
|
if (!req.user) return false;
|
|
if (isStaff(req.user)) return true;
|
|
return { user: { equals: req.user.id } };
|
|
},
|
|
create: ({ req }) => !!req.user,
|
|
update: ({ req }) => {
|
|
if (!req.user) return false;
|
|
if (isStaff(req.user)) return true;
|
|
return { user: { equals: req.user.id } };
|
|
},
|
|
delete: ({ req }) => isStaff(req.user),
|
|
},
|
|
fields: [
|
|
{
|
|
name: "user",
|
|
type: "relationship",
|
|
relationTo: "users",
|
|
required: true,
|
|
index: true,
|
|
},
|
|
{
|
|
name: "beat",
|
|
type: "relationship",
|
|
relationTo: "story-beats",
|
|
required: true,
|
|
index: true,
|
|
},
|
|
{
|
|
name: "readAt",
|
|
type: "date",
|
|
admin: {
|
|
description: "When the user first read the beat.",
|
|
},
|
|
},
|
|
{
|
|
name: "reaction",
|
|
type: "select",
|
|
options: [
|
|
{ label: "Like", value: "like" },
|
|
{ label: "Heart", value: "heart" },
|
|
{ label: "Salute", value: "salute" },
|
|
],
|
|
admin: {
|
|
description: "The user's current reaction to the beat, if any.",
|
|
},
|
|
},
|
|
],
|
|
};
|