feat: implement Project Management with Gantt Chart, Milestones, and CRM enhancements

This commit is contained in:
2026-03-01 00:26:59 +01:00
parent 4b5609a75e
commit 6444cf1e81
47 changed files with 15312 additions and 7373 deletions

View File

@@ -7,9 +7,11 @@ export const CrmContacts: CollectionConfig = {
plural: "Contacts",
},
admin: {
useAsTitle: "email", // Fallback, will define an afterRead hook or virtual field for a better title
defaultColumns: ["firstName", "lastName", "email", "account"],
useAsTitle: "fullName",
defaultColumns: ["fullName", "email", "account"],
group: "CRM",
description:
"Contacts are the individual people linked to an Account. A person should only be created once and can be assigned to a company here.",
},
access: {
read: ({ req: { user } }) => Boolean(user),
@@ -17,7 +19,36 @@ export const CrmContacts: CollectionConfig = {
update: ({ req: { user } }) => Boolean(user),
delete: ({ req: { user } }) => Boolean(user),
},
hooks: {
beforeChange: [
({ data }) => {
if (data?.firstName || data?.lastName) {
data.fullName =
`${data.firstName || ""} ${data.lastName || ""}`.trim();
}
return data;
},
],
afterRead: [
({ doc }) => {
if (!doc.fullName && (doc.firstName || doc.lastName)) {
return {
...doc,
fullName: `${doc.firstName || ""} ${doc.lastName || ""}`.trim(),
};
}
return doc;
},
],
},
fields: [
{
name: "fullName",
type: "text",
admin: {
hidden: true,
},
},
{
type: "row",
fields: [
@@ -44,6 +75,9 @@ export const CrmContacts: CollectionConfig = {
type: "email",
required: true,
unique: true,
admin: {
description: "Primary email address for communication tracking.",
},
},
{
type: "row",
@@ -60,6 +94,7 @@ export const CrmContacts: CollectionConfig = {
type: "text",
admin: {
width: "50%",
placeholder: "https://linkedin.com/in/...",
},
},
],
@@ -68,12 +103,29 @@ export const CrmContacts: CollectionConfig = {
name: "role",
type: "text",
label: "Job Title / Role",
admin: {
description: "e.g. CEO, Marketing Manager, Technical Lead",
},
},
{
name: "account",
type: "relationship",
relationTo: "crm-accounts",
label: "Company / Account",
admin: {
description:
"Link this person to an organization from the Accounts collection.",
},
},
{
name: "interactions",
type: "join",
collection: "crm-interactions",
on: "contact",
admin: {
description:
"Timeline of all communication logged directly with this person.",
},
},
],
};