import type { CollectionConfig } from 'payload' import { createAccess } from './access/create' import { readAccess } from './access/read' import { updateAndDeleteAccess } from './access/updateAndDelete' import { externalUsersLogin } from './endpoints/externalUsersLogin' import { ensureUniqueUsername } from './hooks/ensureUniqueUsername' import { isSuperAdmin } from '@/access/isSuperAdmin' import { setCookieBasedOnDomain } from './hooks/setCookieBasedOnDomain' import { tenantsArrayField } from '@payloadcms/plugin-multi-tenant/fields' const defaultTenantArrayField = tenantsArrayField({ tenantsArrayFieldName: 'tenants', tenantsArrayTenantFieldName: 'tenant', tenantsCollectionSlug: 'tenants', arrayFieldAccess: {}, tenantFieldAccess: {}, rowFields: [ { name: 'roles', type: 'select', defaultValue: ['tenant-viewer'], hasMany: true, options: ['tenant-admin', 'tenant-viewer'], required: true, access: { update: ({ req }) => { const { user } = req if (!user) { return false } if (isSuperAdmin(user)) { return true } return true }, }, }, ], }) const Users: CollectionConfig = { slug: 'users', access: { create: createAccess, delete: updateAndDeleteAccess, read: readAccess, update: updateAndDeleteAccess, }, admin: { useAsTitle: 'email', }, auth: true, endpoints: [externalUsersLogin], fields: [ { type: 'text', name: 'password', hidden: true, access: { read: () => false, // Hide password field from read access update: ({ req, id }) => { const { user } = req if (!user) { return false } if (id === user.id) { // Allow user to update their own password return true } return isSuperAdmin(user) }, }, }, { admin: { position: 'sidebar', }, name: 'roles', type: 'select', defaultValue: ['user'], hasMany: true, options: ['super-admin', 'user'], access: { update: ({ req }) => { return isSuperAdmin(req.user) }, }, }, { name: 'username', type: 'text', hooks: { beforeValidate: [ensureUniqueUsername], }, index: true, }, { ...defaultTenantArrayField, admin: { ...(defaultTenantArrayField?.admin || {}), position: 'sidebar', }, }, ], // The following hook sets a cookie based on the domain a user logs in from. // It checks the domain and matches it to a tenant in the system, then sets // a 'payload-tenant' cookie for that tenant. hooks: { afterLogin: [setCookieBasedOnDomain], }, } export default Users