Concepts
The SCM application has a multi-model approach to represent external business relationships:
graph TD
User --> Party
User --> Partner
User --> Partnership
User --> OrgRelation
receiptParty
Transaction Entity Low-level entity for POs, Invoices, Shipments. OpenBoxes-style.
buildingPartner
Operational Management SCM-native partner with addresses, contacts, and locations.
handshakePartnership
Cross-Organization Formal B2B relationships between separate Organizations.
sitemapOrganizationRelation
Hierarchy Structural relationships (Subsidiary, Division, Partner).
Purpose: Low-level transactional entity for Purchase Orders, Invoices, Shipments.
1model Party {2 id String3 organizationId String4 partyTypeId String "cmt">// Links to PartyType (Supplier, Customer, etc.)5 class String "cmt">// ORGANIZATION or PERSON6 name String7 roles PartyRole[] "cmt">// Used in transactions8 supplierPurchaseOrders PurchaseOrder[] @relation("POSupplier")9 invoicesFrom Invoice[]10 invoicesTo Invoice[]11}PurchaseOrder.supplierPartyId → references a PartyProductSupplier.supplierId → links products to their suppliersInvoice.partyId → billing party| Role | Description | | :--- | :--- | | SUPPLIER | Vendor you buy from | | CUSTOMER | Organization you sell to | | MANUFACTURER | Product manufacturer | | DISTRIBUTOR | Distribution partner | | THIRD_PARTY_LOGISTICS | 3PL provider |
Purpose: SCM-native partner management with addresses, contacts, locations.
1model Partner {2 id String3 organizationId String "cmt">// Your org owns this partner record4 name String5 type PartnerType "cmt">// SUPPLIER, CUSTOMER, CARRIER, etc.6 status PartnerStatus "cmt">// ACTIVE, INACTIVE, SUSPENDED7 8 "cmt">// Operational settings9 taxId String?10 paymentTerms String?11 incoterm String?12 centralPurchasing Boolean13 poPrefix String? "cmt">// For PO numbering14 15 "cmt">// Related data16 addresses PartnerAddress[]17 contacts PartnerContact[]18 locations PartnerLocation[] "cmt">// Links to shared locations19}Purpose: Formal B2B relationships between separate Organizations.
1model Partnership {2 id String3 organizationId String "cmt">// Requesting org4 partnerOrganizationId String "cmt">// Partner org5 status PartnershipStatus "cmt">// REQUESTED, ACCEPTED, DENIED6 partyRole PartyRoleType "cmt">// Role they play for you7 relationshipType RelationshipType "cmt">// BUYER_SELLER, LOGISTICS, etc.8 9 "cmt">// Invitation workflow10 invitationToken String?11 invitationEmail String?12 invitationSentAt DateTime?13 invitationAcceptedAt DateTime?14}sequenceDiagram
participant Org A as Org A (Requester)
participant Invite as Invitation
participant Org B as Org B (Partner)
Org A->>Invite: Request
Note right of Invite: PENDING
Invite->>Org B: Accept
Note right of Org B: Active Partnership
Purpose: Define structural relationships between organizations (including PARTNER role).
1model OrganizationRelation {2 parentOrgId String3 childOrgId String4 role String "cmt">// SUBSIDIARY, DIVISION, PARTNER, AFFILIATE5 isActive Boolean6}| Role | Description | Billing Included | | :--- | :--- | :--- | | SUBSIDIARY | Owned subsidiary | ✅ Yes | | DIVISION | Business division | ✅ Yes | | BRANCH | Branch office | ✅ Yes | | PARTNER | External partner | ❌ No | | AFFILIATE | Affiliate org | ❌ No | | FRANCHISE | Franchise | ❌ No |
Supplier → Party record (type: SUPPLIER)supplierPartyId = Party.id/api/partners)The partners API aggregates from 3 sources:
1"cmt">// 1. Partner model (owned by your org)2const partnersFromModel = await database.partner.findMany({3 where: { organizationId, type: 'SUPPLIER' }4});5 6"cmt">// 2. OrganizationRelation (PARTNER role)7const partnersFromRelations = await database.organizationRelation.findMany({8 where: { parentOrgId: organizationId, role: 'PARTNER' }9});10 11"cmt">// 3. Partnership model (accepted partnerships)12const partnersFromPartnerships = await database.partnership.findMany({13 where: { organizationId, status: 'ACCEPTED' }14});1model Organization {2 isCustomer Boolean "cmt">// Can be sold to3 isSupplier Boolean "cmt">// Can be purchased from4 partnershipTier PartnershipTier? "cmt">// PARTNER_ONLY, BASIC, FULL5}These flags determine:
isSupplier=true → Appears in supplier dropdowns for POsisCustomer=true → Appears in customer dropdowns for Sales OrderspartnershipTier → Controls what partnership features are available| Model | Purpose | Scope | Used For | | :--- | :--- | :--- | :--- | | Party | Transaction entity | Per-org | POs, Invoices, Shipments | | Partner | Operational config | Per-org | Addresses, contacts, terms | | Partnership | Cross-org link | Multi-org | Visibility, collaboration | | OrganizationRelation | Org hierarchy | Multi-org | Subsidiaries, partners, billing |
