Skip to content

Orders and Commerce

Overview

The commerce domain in CoCore manages the business side of print production, connecting customer orders to production jobs. Unlike traditional JDF which focuses on production, CoCore provides comprehensive order management, customer relationships, and financial tracking.

Domain Structure

Customer
├── Contacts (multiple contact persons)
├── Addresses (billing, shipping, etc.)
└── Orders
    ├── OrderLines (line items)
    │   └── Job (production link)
    └── OrderShippingInstructions
        └── OrderLineShippingInstructions (override per line)

Order Lifecycle

Order States

graphql
enum OrderStateEnum {
  DRAFT             # Initial creation, not submitted
  PENDING           # Submitted, awaiting confirmation
  CONFIRMED         # Accepted and ready for production
  IN_PRODUCTION     # Being manufactured
  READY_FOR_PICKUP  # Complete, awaiting collection
  DELIVERED         # Shipped/collected by customer
  CANCELLED         # Order cancelled
}

Order Flow

DRAFT → PENDING → CONFIRMED → IN_PRODUCTION → READY_FOR_PICKUP → DELIVERED
          ↓           ↓             ↓                ↓
      CANCELLED   CANCELLED     CANCELLED        CANCELLED

Customer Management

Creating Customers

graphql
mutation CreateCustomer {
  createCustomer(input: {
    # Basic Information
    businessName: "ACME Printing Co."
    contactName: "John Smith"
    contactEmail: "john@acmeprinting.com"
    phone: "+1-555-0100"

    # Customer Type
    customerType: BUSINESS  # or INDIVIDUAL

    # Financial
    taxId: "12-3456789"
    paymentTerms: 30  # Net 30 days
    creditLimit: { amount: 50000, currency: "USD" }

    # Status
    status: ACTIVE  # ACTIVE, INACTIVE, SUSPENDED, PROSPECT

    # External Reference
    externalId: "CRM-CUST-001"
  }) {
    result {
      id
      businessName
      status
      creditLimit {
        amount
        currency
      }
    }
    errors {
      field
      message
    }
  }
}

Adding Customer Addresses

graphql
mutation AddCustomerAddress {
  createAddress(input: {
    customerId: "customer-123"

    # Address Type
    addressType: BILLING  # BILLING, SHIPPING, BOTH

    # Address Details
    name: "ACME Headquarters"
    line1: "123 Main Street"
    line2: "Suite 400"
    city: "Springfield"
    state: "IL"
    postalCode: "62701"
    country: "US"

    # Flags
    isDefault: true
    isActive: true
  }) {
    result {
      id
      addressType
      isDefault
    }
  }
}

Adding Customer Contacts

graphql
mutation AddCustomerContact {
  createContact(input: {
    customerId: "customer-123"

    # Contact Information
    firstName: "Jane"
    lastName: "Doe"
    title: "Production Manager"
    email: "jane.doe@acmeprinting.com"
    phone: "+1-555-0101"
    mobile: "+1-555-0102"

    # Preferences
    isPrimary: true
    receiveOrderUpdates: true
    receiveInvoices: false
    receiveProofs: true
  }) {
    result {
      id
      firstName
      lastName
      email
      isPrimary
    }
  }
}

Creating Orders

Basic Order Creation

graphql
mutation CreateBasicOrder {
  createOrder(input: {
    # Required Fields
    orderNumber: "ORD-2024-001"
    orderDate: "2024-02-15"
    customerId: "customer-123"

    # Delivery Dates
    requestedDeliveryDate: "2024-03-01"
    promisedDeliveryDate: "2024-02-28"

    # Order Type
    rushOrder: false

    # Initial State
    state: DRAFT
  }) {
    result {
      id
      orderNumber
      state
      orderDate
      customer {
        businessName
      }
    }
    errors {
      field
      message
    }
  }
}

Complete Order with Financial Details

graphql
mutation CreateCompleteOrder {
  createOrder(input: {
    orderNumber: "ORD-2024-002"
    orderDate: "2024-02-15"
    customerId: "customer-456"
    contactId: "contact-789"  # Specific contact person

    # Dates
    requestedDeliveryDate: "2024-02-25"
    promisedDeliveryDate: "2024-02-24"

    # Financial (Money type includes amount and currency)
    subtotal: { amount: 1500.00, currency: "USD" }
    taxAmount: { amount: 120.00, currency: "USD" }
    shippingAmount: { amount: 50.00, currency: "USD" }
    discountAmount: { amount: 75.00, currency: "USD" }
    totalAmount: { amount: 1595.00, currency: "USD" }

    # Payment
    paymentStatus: PENDING  # PENDING, PARTIAL, PAID, OVERDUE, REFUNDED
    paymentMethod: CREDIT_CARD  # CASH, CHECK, CREDIT_CARD, WIRE_TRANSFER, TERMS

    # Rush Order
    rushOrder: true
    rushFee: { amount: 200.00, currency: "USD" }

    # Instructions
    specialInstructions: "Call before delivery. Use loading dock entrance."

    state: PENDING
  }) {
    result {
      id
      orderNumber
      totalAmount {
        amount
        currency
      }
      paymentStatus
    }
  }
}

Order Lines

Adding Order Lines

graphql
mutation AddOrderLines {
  # Line 1: Business Cards
  line1: createOrderLine(input: {
    orderId: "order-123"
    lineNumber: 1

    # Product Information
    productName: "Business Cards - Premium"
    productSku: "BC-PREM-001"
    description: "Full color, double-sided, UV coating"

    # Quantities
    quantity: 1000
    minDeliverableQuantity: 950   # Allow 5% under
    maxDeliverableQuantity: 1100  # Allow 10% over

    # Pricing
    unitPrice: { amount: 0.15, currency: "USD" }
    lineTotal: { amount: 150.00, currency: "USD" }

    # Tax and Fees
    taxRate: 0.08  # 8% tax
    taxAmount: { amount: 12.00, currency: "USD" }
    discountAmount: { amount: 0.00, currency: "USD" }
    shippingAmount: { amount: 5.00, currency: "USD" }

    # Proofing
    proofRequired: HARD_COPY  # NONE, SOFT_COPY, HARD_COPY
    proofApproved: false

    # State
    state: PENDING  # PENDING, CONFIRMED, IN_PRODUCTION, COMPLETE, CANCELLED

    # Link to production (optional at creation)
    jobId: null  # Will link when job is created
  }) {
    result {
      id
      lineNumber
      productName
      quantity
      lineTotal {
        amount
        currency
      }
    }
  }

  # Line 2: Brochures
  line2: createOrderLine(input: {
    orderId: "order-123"
    lineNumber: 2
    productName: "Tri-fold Brochures"
    productSku: "BR-TRI-001"
    quantity: 5000
    unitPrice: { amount: 0.25, currency: "USD" }
    lineTotal: { amount: 1250.00, currency: "USD" }
    taxRate: 0.08
    taxAmount: { amount: 100.00, currency: "USD" }
    proofRequired: SOFT_COPY
    state: PENDING
  }) {
    result {
      id
      lineNumber
      productName
    }
  }
}

Linking Order Lines to Jobs

graphql
mutation LinkOrderLineToJob {
  updateOrderLine(
    id: "order-line-123"
    input: {
      jobId: "job-456"
      state: IN_PRODUCTION
    }
  ) {
    result {
      id
      job {
        id
        jobNumber
        name
      }
      state
    }
  }
}

Shipping Instructions

Order-Level Shipping

graphql
mutation AddOrderShipping {
  createOrderShippingInstruction(input: {
    orderId: "order-123"
    instructionNumber: 1

    # Shipping Details
    shippingMethod: "FedEx Ground"
    shippingCost: { amount: 50.00, currency: "USD" }

    # Delivery
    deliveryDate: "2024-02-28"
    deliveryTime: "09:00-17:00"

    # Address (can override customer default)
    addressId: "address-456"

    # Special Instructions
    specialInstructions: "Leave at reception desk"
    signatureRequired: true

    # Package Details
    numberOfPackages: 2
    packageWeight: { value: 10.5, unit: "KG" }
    packageDimensions: "40x30x20 cm"
  }) {
    result {
      id
      shippingMethod
      deliveryDate
      trackingNumber  # Added when shipped
    }
  }
}

Line-Item Specific Shipping

graphql
mutation AddLineItemShipping {
  createOrderLineShippingInstruction(input: {
    orderLineId: "order-line-456"
    instructionNumber: 1

    # Override order-level shipping for this line
    shippingMethod: "Next Day Air"
    shippingCost: { amount: 125.00, currency: "USD" }

    # Different delivery address
    addressId: "address-789"

    deliveryDate: "2024-02-20"  # Earlier than rest of order
    specialInstructions: "Urgent - deliver to warehouse"
  }) {
    result {
      id
      orderLine {
        productName
      }
      shippingMethod
      deliveryDate
    }
  }
}

Querying Orders

Get Order with Full Details

graphql
query GetOrderComplete {
  getOrder(id: "order-123") {
    id
    orderNumber
    state

    # Dates
    orderDate
    requestedDeliveryDate
    promisedDeliveryDate
    actualDeliveryDate

    # Financial Summary
    subtotal { amount, currency }
    taxAmount { amount, currency }
    shippingAmount { amount, currency }
    discountAmount { amount, currency }
    totalAmount { amount, currency }

    # Payment
    paymentStatus
    paymentMethod

    # Rush Order
    rushOrder
    rushFee { amount, currency }

    # Special Instructions
    specialInstructions

    # Delivery
    deliveryStatus  # PENDING, SHIPPED, DELIVERED, RETURNED

    # Customer
    customer {
      id
      businessName
      contactEmail
      paymentTerms
      creditLimit { amount, currency }
      status
    }

    # Contact Person
    contact {
      firstName
      lastName
      email
      phone
    }

    # Order Lines
    lines {
      id
      lineNumber
      productName
      productSku
      description
      quantity
      minDeliverableQuantity
      maxDeliverableQuantity
      unitPrice { amount, currency }
      lineTotal { amount, currency }
      taxAmount { amount, currency }
      proofRequired
      proofApproved
      proofApprovedAt
      state

      # Linked Job
      job {
        id
        jobNumber
        name
        status
      }

      # Line-specific shipping
      shippingInstructions {
        shippingMethod
        deliveryDate
        trackingNumber
      }
    }

    # Addresses
    addresses {
      id
      addressType
      line1
      line2
      city
      state
      postalCode
      country
    }

    # Order-level shipping
    shippingInstructions {
      instructionNumber
      shippingMethod
      shippingCost { amount, currency }
      deliveryDate
      trackingNumber
      specialInstructions
    }
  }
}

Search Orders

graphql
query SearchOrders {
  listOrders(
    filter: {
      # By customer
      customer: {
        businessName: { ilike: "%acme%" }
      }

      # By state
      state: { in: [PENDING, CONFIRMED, IN_PRODUCTION] }

      # By dates
      orderDate: {
        greaterThanOrEqual: "2024-01-01"
        lessThan: "2024-02-01"
      }

      # By payment
      paymentStatus: { in: [PENDING, OVERDUE] }

      # Rush orders only
      rushOrder: { eq: true }

      # By amount
      totalAmount: {
        amount: { greaterThanOrEqual: 1000 }
      }
    }
    sort: [
      { field: ORDER_DATE, order: DESC }
    ]
    first: 20
  ) {
    count
    results {
      id
      orderNumber
      customer { businessName }
      orderDate
      totalAmount { amount, currency }
      paymentStatus
      state
    }
    endKeyset
  }
}

Common Workflows

Quote to Order Conversion

graphql
mutation ConvertQuoteToOrder {
  # Step 1: Create order from quote/estimate
  createOrder(input: {
    orderNumber: "ORD-2024-100"
    customerId: $customerId
    orderDate: $today
    state: PENDING

    # Copy financial details from quote
    subtotal: $quoteSubtotal
    taxAmount: $quoteTax
    totalAmount: $quoteTotal

    requestedDeliveryDate: $requestedDate
  }) {
    result {
      id
      orderNumber
    }
  }
}

# Step 2: Copy estimate items to order lines
mutation CopyEstimateItems {
  createOrderLine(input: {
    orderId: $orderId
    lineNumber: $lineNumber
    productName: $estimateItemName
    quantity: $estimateQuantity
    unitPrice: $estimateUnitPrice
    lineTotal: $estimateLineTotal
    state: PENDING
  }) {
    result { id }
  }
}

Order Confirmation Workflow

graphql
# Step 1: Validate credit
query CheckCustomerCredit {
  getCustomer(id: $customerId) {
    creditLimit { amount }
    # Check current outstanding balance
    orders(filter: {
      paymentStatus: { in: [PENDING, PARTIAL, OVERDUE] }
    }) {
      results {
        totalAmount { amount }
      }
    }
  }
}

# Step 2: Confirm order
mutation ConfirmOrder {
  updateOrder(
    id: $orderId
    input: {
      state: CONFIRMED
      promisedDeliveryDate: $calculatedDeliveryDate
    }
  ) {
    result {
      state
      promisedDeliveryDate
    }
  }
}

# Step 3: Create production jobs
mutation CreateJobsForOrder {
  createJob(input: {
    name: $orderLineProductName
    externalId: $orderNumber
    orderedQuantity: $orderLineQuantity
    maxDeliverableQuantity: $orderLineMaxQuantity
    billingCustomerId: $customerId
    deliveryCustomerId: $customerId
    orderLineId: $orderLineId
  }) {
    result {
      id
      jobNumber
    }
  }
}

Payment Processing

graphql
mutation RecordPayment {
  # Update order payment status
  updateOrder(
    id: "order-123"
    input: {
      paymentStatus: PAID
      paymentMethod: CREDIT_CARD
      # Record payment reference
      metadata: {
        paymentReference: "STRIPE-ch_1234567890"
        paymentDate: "2024-02-15T10:30:00Z"
      }
    }
  ) {
    result {
      id
      paymentStatus
    }
  }

  # Create payment record (if separate payment tracking exists)
  createPayment(input: {
    orderId: "order-123"
    amount: { amount: 1595.00, currency: "USD" }
    method: CREDIT_CARD
    reference: "STRIPE-ch_1234567890"
    status: COMPLETED
  }) {
    result {
      id
      reference
    }
  }
}

Shipping and Fulfillment

graphql
mutation ShipOrder {
  # Update shipping instruction with tracking
  updateOrderShippingInstruction(
    id: "shipping-instruction-123"
    input: {
      trackingNumber: "1Z999AA10123456784"
      actualShippingDate: "2024-02-28T14:30:00Z"
      carrier: "UPS"
    }
  ) {
    result {
      trackingNumber
    }
  }

  # Update order delivery status
  updateOrder(
    id: "order-123"
    input: {
      deliveryStatus: SHIPPED
      state: DELIVERED
      actualDeliveryDate: "2024-03-01"
    }
  ) {
    result {
      state
      deliveryStatus
    }
  }

  # Send shipping notification
  sendShippingNotification(input: {
    orderId: "order-123"
    recipientEmail: $customerEmail
    trackingNumbers: ["1Z999AA10123456784"]
  }) {
    result {
      sentAt
    }
  }
}

Pricing and Billing

Dynamic Pricing Calculation

graphql
query CalculateOrderPricing {
  calculatePricing(input: {
    customerId: "customer-123"
    items: [
      {
        productSku: "BC-PREM-001"
        quantity: 1000
        options: {
          coating: "UV"
          sides: "double"
          rushOrder: true
        }
      }
    ]
  }) {
    subtotal { amount, currency }
    rushFee { amount, currency }
    volumeDiscount { amount, currency }
    taxAmount { amount, currency }
    shippingAmount { amount, currency }
    totalAmount { amount, currency }

    # Breakdown per item
    itemPricing {
      productSku
      basePrice { amount, currency }
      optionsPrice { amount, currency }
      quantity
      lineTotal { amount, currency }
    }
  }
}

Invoice Generation

graphql
mutation GenerateInvoice {
  createInvoice(input: {
    orderId: "order-123"
    invoiceNumber: "INV-2024-001"
    invoiceDate: "2024-03-01"
    dueDate: "2024-03-31"  # Net 30

    # Can override order amounts if needed
    subtotal: { amount: 1500.00, currency: "USD" }
    taxAmount: { amount: 120.00, currency: "USD" }
    totalAmount: { amount: 1620.00, currency: "USD" }

    # Billing address
    billingAddressId: "address-billing-123"

    # Terms
    paymentTerms: "Net 30"
    notes: "Thank you for your business!"
  }) {
    result {
      id
      invoiceNumber
      totalAmount { amount, currency }
      dueDate
    }
  }
}

Best Practices

1. Order Number Generation

Use a consistent format for order numbers:

ORD-YYYY-NNNN (e.g., ORD-2024-0001)

2. Payment Terms Management

Always check credit limits before confirming orders:

graphql
paymentTerms: 30  # Days
creditLimit: { amount: 50000, currency: "USD" }

3. Quantity Tolerance

Set realistic min/max quantities for print production:

graphql
quantity: 1000
minDeliverableQuantity: 950   # -5%
maxDeliverableQuantity: 1100  # +10%

4. Proof Management

Track proof requirements and approvals:

graphql
proofRequired: HARD_COPY
proofApproved: true
proofApprovedAt: "2024-02-20T10:30:00Z"

5. State Transitions

Follow proper order state flow:

  • Only confirm orders after credit check
  • Link to jobs before moving to IN_PRODUCTION
  • Verify shipping details before READY_FOR_PICKUP

6. Financial Accuracy

Always use Money type with currency:

graphql
unitPrice: { amount: 0.15, currency: "USD" }

Dashboard Queries

Orders Dashboard

graphql
query OrdersDashboard {
  # Today's orders
  todaysOrders: listOrders(
    filter: {
      orderDate: {
        greaterThanOrEqual: $todayStart
        lessThan: $todayEnd
      }
    }
  ) {
    count
    results {
      orderNumber
      customer { businessName }
      totalAmount { amount }
    }
  }

  # Pending payments
  pendingPayments: listOrders(
    filter: {
      paymentStatus: { in: [PENDING, OVERDUE] }
    }
  ) {
    count
    results {
      orderNumber
      totalAmount { amount }
      paymentStatus
      customer { businessName }
    }
  }

  # Orders awaiting production
  awaitingProduction: listOrders(
    filter: {
      state: { eq: CONFIRMED }
    }
  ) {
    count
    results {
      orderNumber
      promisedDeliveryDate
    }
  }

  # Rush orders
  rushOrders: listOrders(
    filter: {
      rushOrder: { eq: true }

Connect. Combine. Collaborate.
The pioneering open integration platform, dedicated to transforming connectivity in the printing industry.