// ============================================================ // INSIGHT CRM Service - Prisma Schema // ============================================================ // Eigenes Schema im PostgreSQL-Schema 'app_crm' // Eigener Prisma-Client-Output (kein Konflikt mit Core) // ============================================================ generator client { provider = "prisma-client-js" output = "../node_modules/.prisma/crm-client" } datasource db { provider = "postgresql" url = env("DATABASE_URL") directUrl = env("DATABASE_URL_DIRECT") schemas = ["app_crm"] } // -------------------------------------------------------- // Company - Unternehmen (uebergeordnete Entity) // -------------------------------------------------------- model Company { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid name String @db.VarChar(200) industry String? @db.VarChar(100) // Kontaktdaten email String? @db.VarChar(255) phone String? @db.VarChar(50) website String? @db.VarChar(500) // Adresse street String? @db.VarChar(200) zip String? @db.VarChar(20) city String? @db.VarChar(100) state String? @db.VarChar(100) country String? @default("DE") @db.VarChar(2) // Zusaetzlich notes String? @db.Text tags String[] @default([]) isActive Boolean @default(true) @map("is_active") // Lexware Office Integration lexwareContactId String? @map("lexware_contact_id") @db.VarChar(36) lexwareContactVersion Int? @map("lexware_contact_version") lexwareSyncedAt DateTime? @map("lexware_synced_at") // Audit-Trail createdBy String @map("created_by") @db.Uuid updatedBy String? @map("updated_by") @db.Uuid createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen contacts Contact[] deals Deal[] lexwareVouchers LexwareVoucher[] @@unique([tenantId, lexwareContactId]) @@index([tenantId]) @@index([tenantId, name]) @@index([tenantId, industry]) @@index([tenantId, isActive]) @@map("companies") @@schema("app_crm") } // -------------------------------------------------------- // Contact - CRM-Kontakte (Personen) // -------------------------------------------------------- model Contact { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid type ContactType @default(PERSON) // Person firstName String? @map("first_name") @db.VarChar(100) lastName String? @map("last_name") @db.VarChar(100) // Unternehmenszuordnung companyId String? @map("company_id") @db.Uuid companyName String? @map("company_name") @db.VarChar(200) position String? @db.VarChar(200) // Kontaktdaten email String? @db.VarChar(255) phone String? @db.VarChar(50) mobile String? @db.VarChar(50) website String? @db.VarChar(500) // Adresse street String? @db.VarChar(200) zip String? @db.VarChar(20) city String? @db.VarChar(100) state String? @db.VarChar(100) country String? @default("DE") @db.VarChar(2) // Zusaetzlich notes String? @db.Text tags String[] @default([]) isActive Boolean @default(true) @map("is_active") // Lexware Office Integration lexwareContactId String? @map("lexware_contact_id") @db.VarChar(36) lexwareContactVersion Int? @map("lexware_contact_version") lexwareSyncedAt DateTime? @map("lexware_synced_at") // Audit-Trail (User-IDs aus platform_core) createdBy String @map("created_by") @db.Uuid updatedBy String? @map("updated_by") @db.Uuid createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen company Company? @relation(fields: [companyId], references: [id], onDelete: SetNull) activities Activity[] deals Deal[] lexwareVouchers LexwareVoucher[] @@unique([tenantId, lexwareContactId]) @@index([tenantId]) @@index([tenantId, email]) @@index([tenantId, companyId]) @@index([tenantId, companyName]) @@index([tenantId, lastName, firstName]) @@index([tenantId, isActive]) @@map("contacts") @@schema("app_crm") } enum ContactType { PERSON ORGANIZATION @@schema("app_crm") } // -------------------------------------------------------- // Activity - CRM-Aktivitaeten (Notizen, Anrufe, E-Mails) // -------------------------------------------------------- model Activity { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid contactId String @map("contact_id") @db.Uuid type ActivityType subject String @db.VarChar(500) description String? @db.Text // Terminierung scheduledAt DateTime? @map("scheduled_at") completedAt DateTime? @map("completed_at") // Audit-Trail createdBy String @map("created_by") @db.Uuid updatedBy String? @map("updated_by") @db.Uuid createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen contact Contact @relation(fields: [contactId], references: [id], onDelete: Cascade) @@index([tenantId]) @@index([tenantId, contactId]) @@index([tenantId, type]) @@index([tenantId, scheduledAt]) @@map("activities") @@schema("app_crm") } enum ActivityType { NOTE CALL EMAIL MEETING TASK @@schema("app_crm") } // -------------------------------------------------------- // Pipeline - Sales-Pipelines (konfigurierbar pro Tenant) // -------------------------------------------------------- model Pipeline { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid name String @db.VarChar(200) isDefault Boolean @default(false) @map("is_default") isActive Boolean @default(true) @map("is_active") // Audit-Trail createdBy String @map("created_by") @db.Uuid updatedBy String? @map("updated_by") @db.Uuid createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen stages PipelineStage[] deals Deal[] @@index([tenantId]) @@index([tenantId, isActive]) @@map("pipelines") @@schema("app_crm") } // -------------------------------------------------------- // PipelineStage - Stufen einer Pipeline (z.B. Lead, Angebot) // -------------------------------------------------------- model PipelineStage { id String @id @default(uuid()) @db.Uuid pipelineId String @map("pipeline_id") @db.Uuid name String @db.VarChar(200) sortOrder Int @default(0) @map("sort_order") color String @default("#6B7280") @db.VarChar(7) createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen pipeline Pipeline @relation(fields: [pipelineId], references: [id], onDelete: Cascade) deals Deal[] @@index([pipelineId]) @@index([pipelineId, sortOrder]) @@map("pipeline_stages") @@schema("app_crm") } // -------------------------------------------------------- // Deal - Verkaufschancen / Deals // -------------------------------------------------------- model Deal { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid pipelineId String @map("pipeline_id") @db.Uuid stageId String @map("stage_id") @db.Uuid contactId String? @map("contact_id") @db.Uuid companyId String? @map("company_id") @db.Uuid title String @db.VarChar(500) value Decimal? @db.Decimal(15, 2) currency String @default("EUR") @db.VarChar(3) status DealStatus @default(OPEN) expectedCloseDate DateTime? @map("expected_close_date") closedAt DateTime? @map("closed_at") notes String? @db.Text // Audit-Trail createdBy String @map("created_by") @db.Uuid updatedBy String? @map("updated_by") @db.Uuid createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen pipeline Pipeline @relation(fields: [pipelineId], references: [id], onDelete: Cascade) stage PipelineStage @relation(fields: [stageId], references: [id]) contact Contact? @relation(fields: [contactId], references: [id], onDelete: SetNull) company Company? @relation(fields: [companyId], references: [id], onDelete: SetNull) dealVouchers DealVoucher[] @@index([tenantId]) @@index([tenantId, pipelineId]) @@index([tenantId, stageId]) @@index([tenantId, contactId]) @@index([tenantId, companyId]) @@index([tenantId, status]) @@map("deals") @@schema("app_crm") } enum DealStatus { OPEN WON LOST @@schema("app_crm") } // -------------------------------------------------------- // Lexware Office Integration - Voucher Types // -------------------------------------------------------- enum VoucherType { QUOTATION ORDER_CONFIRMATION INVOICE CREDIT_NOTE @@schema("app_crm") } // -------------------------------------------------------- // LexwareVoucher - Gecachte Belege aus Lexware Office // -------------------------------------------------------- model LexwareVoucher { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid lexwareVoucherId String @map("lexware_voucher_id") @db.VarChar(36) voucherType VoucherType @map("voucher_type") voucherNumber String? @map("voucher_number") @db.VarChar(100) voucherDate DateTime? @map("voucher_date") voucherStatus String? @map("voucher_status") @db.VarChar(50) totalGrossAmount Decimal? @map("total_gross_amount") @db.Decimal(15, 2) totalNetAmount Decimal? @map("total_net_amount") @db.Decimal(15, 2) totalTaxAmount Decimal? @map("total_tax_amount") @db.Decimal(15, 2) currency String @default("EUR") @db.VarChar(3) title String? @db.VarChar(500) lineItemsCount Int? @map("line_items_count") lineItemsJson String? @map("line_items_json") @db.Text // Verknuepfung zu Lexware-Kontakt und CRM-Entitaeten lexwareContactId String @map("lexware_contact_id") @db.VarChar(36) companyId String? @map("company_id") @db.Uuid contactId String? @map("contact_id") @db.Uuid lexwareDeepLink String? @map("lexware_deep_link") @db.VarChar(500) fetchedAt DateTime @default(now()) @map("fetched_at") createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // Relationen company Company? @relation(fields: [companyId], references: [id], onDelete: SetNull) contact Contact? @relation(fields: [contactId], references: [id], onDelete: SetNull) deals DealVoucher[] @@unique([tenantId, lexwareVoucherId]) @@index([tenantId]) @@index([tenantId, companyId]) @@index([tenantId, contactId]) @@index([tenantId, lexwareContactId]) @@index([tenantId, voucherType]) @@map("lexware_vouchers") @@schema("app_crm") } // -------------------------------------------------------- // DealVoucher - Verknuepfung Deal <-> Lexware-Beleg (m:n) // -------------------------------------------------------- model DealVoucher { id String @id @default(uuid()) @db.Uuid tenantId String @map("tenant_id") @db.Uuid dealId String @map("deal_id") @db.Uuid voucherId String @map("voucher_id") @db.Uuid linkedBy String @map("linked_by") @db.Uuid linkedAt DateTime @default(now()) @map("linked_at") // Relationen deal Deal @relation(fields: [dealId], references: [id], onDelete: Cascade) voucher LexwareVoucher @relation(fields: [voucherId], references: [id], onDelete: Cascade) @@unique([dealId, voucherId]) @@index([tenantId]) @@index([tenantId, dealId]) @@index([tenantId, voucherId]) @@map("deal_vouchers") @@schema("app_crm") }