Payments, Invoices and Transactions
Customer Transactions
Anything that costs money in the system is recorded as a transaction under the customer.
Every transaction has a monetary amount for wholesale cost and retail cost, and a description of what the transaction is for.
Transactions can be automatically generated by the system, for example, when a service is provisioned, a transaction is created for the setup cost, and when a service is billed, a transaction is created for the retail cost.
Transactions can also be manually created, for example, if a customer is given a credit, a transaction is created for the credit amount, or an installation fee is charged, a transaction is created for the installation fee.
Transactions are grouped together to form
Invoices <payments_invoices>, which is sent to the customer for
payment.

Accessing Transactions
Transactions can be viewed at the system level or per-customer:
Per-Customer View:
- Navigate to Customers → [Select Customer]
- Click Billing tab
- View transactions list in the first card
System-Wide View:
- Navigate to Billing → Transactions (from main menu)
- View all transactions across all customers
Transaction Statistics Widgets
At the top of the transactions page, four statistics cards display financial summaries:

Widget Descriptions:
- Total Transactions - Sum of all transaction retail costs (all time)
- Total Uninvoiced Transactions - Sum of transactions not yet included in an invoice
- Total Transactions This Month - Sum of transactions created this calendar month
- Total Transactions Last Month - Sum of transactions created last calendar month
Value Formatting:
- Values over 1,000: Display as "k" suffix (e.g., $1.5k)
- Values over 1,000,000: Display as "M" suffix (e.g., $2.3M)
- Values over 1,000,000,000: Display as "B" suffix (e.g., $1.1B)
Transactions List
The transactions table displays all transactions with the following columns:
Column Descriptions:
- ID - Unique transaction ID
- Date - Transaction creation date
- Title - Short transaction name
- Description - Detailed description of what the transaction is for
- Amount - Retail cost (positive for charges, negative for credits)
- Invoice - Invoice ID if transaction has been invoiced (clickable link)
- Status - Checkmark if invoiced, dash if not yet invoiced
Actions Per Row:
Each row has an actions menu (⋮) with options:
- View Details - Opens transaction detail modal
- Download Invoice PDF - Download PDF (only if invoiced)
- Void Transaction - Mark transaction as void (only if not invoiced)
Transaction Types
Transactions fall into two main categories:
Debit Transactions (Charges)
Positive amounts that increase customer balance owed:
- Service Setup Fees - One-time charges when service provisioned
- Monthly Service Fees - Recurring charges for services
- Installation Fees - Charges for field technician visits
- Equipment Charges - Charges for modems, routers, SIM cards
- Late Payment Fees - Penalties for overdue invoices
- Manual Charges - Custom charges added by staff
Credit Transactions (Payments/Refunds)
Negative amounts that decrease customer balance owed:
- Cash Payments - Customer paid by cash
- Card Payments - Customer paid by credit/debit card
- Bank Transfer Payments - Customer paid via bank transfer
- Account Credits - Goodwill credits, compensation
- Refunds - Money returned to customer
- Discounts - Promotional or loyalty discounts
Adding a Transaction Manually
Click "+ Add Transaction" to open the add transaction modal.
Debit Transaction (Charge):

Credit Transaction (Payment/Refund):

Field Descriptions:
- Transaction Type - Select Debit (charge) or Credit (payment/refund)
- Credit Type - If Credit selected, choose payment method (Cash, Card, Bank Transfer)
- Title - Short name for transaction (required)
- Description - Detailed explanation (optional)
- Retail Cost - Amount customer pays (required, positive number)
- Wholesale Cost - Your cost (optional, for margin tracking)
- Tax Percentage - Tax rate applied to this transaction (optional, defaults to product tax or 0%)
- Service - Link transaction to specific service (optional)
- Site - Link transaction to specific site (optional)
- Transaction Date - Date of transaction (defaults to today)
Validation:
- Title and retail cost are required
- Retail cost must be a positive number
- If Credit type selected, a credit type must be chosen
What Happens:
- Transaction created in database
- Appears in customer's transactions list
- Included in "Uninvoiced Transactions" count
- Available for inclusion in next invoice generation
- Activity log entry created
Searching and Filtering Transactions
Search
Use the search bar to find transactions. Searches across:
- Transaction ID
- Title
- Description
- Invoice ID
Filters
Apply filters to narrow transaction list:
Available Filters:
- Void Status - All, Void, Not Void
- Invoice Status - All, Invoiced, Not Invoiced
Filter Actions:
- Apply Filters - Apply selected filters to list
- Reset Filters - Clear all filters and show all transactions
Sorting
Click any column header to sort:
- ID - Sort by transaction ID (newest/oldest)
- Date - Sort by transaction date
- Title - Sort alphabetically
- Amount - Sort by retail cost (highest/lowest)
- Invoice - Sort by invoice ID
Click again to reverse sort direction (ascending ↔ descending).
Voiding Transactions
Transactions added in error can be voided (marked as deleted).
Requirements:
- Transaction must NOT be invoiced
- Once invoiced, transactions cannot be voided (must be refunded instead)
How to Void:
- Locate transaction in list
- Click actions menu (⋮)
- Select "Void Transaction"
- Confirm in modal

What Happens:
- Transaction marked as
void = true - No longer appears in default transaction list
- Excluded from invoice generation
- Can be viewed by filtering for "Void" transactions
- Deducted from "Uninvoiced Transactions" total
Wallet-linked transactions (wallet_ledger_id set):
- Wallet balance is reversed before void (debit to undo a credit, credit to undo a debit)
- Add Funds card top-up (
payment_type=wallet_topup_card): wallet debited and card refunded - Cash top-up / wallet invoice payment / other wallet lines: wallet adjusted only; no card refund
- Insufficient wallet: void fails if topped-up funds were already spent (transaction stays active)
Service / provisioning charges from hybrid capture usually have no wallet_ledger_id on the
billing line. Voiding those lines only sets void=true today; full wallet credit for service voids is
planned on the financial-documents branch.
API: DELETE /crm/transaction/transaction_id/{transaction_id} — see
payment_system_guide.md — Void Transaction.
Note: Voiding is NOT the same as refunding. Void means "this transaction should never have existed." Refund means "reverse a valid transaction."
Tax on Transactions
Transactions can include tax, which is automatically calculated based on the product's tax configuration or manually specified per transaction.

Tax Behavior:
- Debit Transactions (Charges) - Tax is applied to charges based on:
- Product Tax Percentage - If the transaction is linked to a product, the product's tax percentage is automatically applied
- Manual Override - Staff can override the tax percentage when creating a transaction
- Tax Amount - Calculated as:
retail_cost × (tax_percentage / 100) - Display Format - Shown as:
$10.00 (10%)in transaction lists
- Credit Transactions (Payments/Refunds) - No tax is applied to
credits
- Tax percentage field is hidden for credit transactions
- Tax is automatically set to 0% for all payments and refunds
- Credits reduce the customer's outstanding balance without tax implications
Tax Calculation Example:
- Product: Mobile Plan with 10% tax, $50.00 retail cost
- Automatic Tax Calculation: $50.00 × 0.10 = $5.00
- Display: $5.00 (10%)
Zero Tax (NIL/Exempt):
- Products can be tax-exempt by setting tax percentage to 0
- Tax defaults to 0% if not specified
- Tax-exempt transactions show "-" in the Tax column

Transaction Details View
Click a transaction to view full details:
Invoiced vs Uninvoiced Transactions
Uninvoiced Transactions:
- Not yet included in any invoice
- Available for next invoice generation
- Can be voided
- Count toward "Uninvoiced Transactions" total
- Status shows dash (-)
Invoiced Transactions:
- Included in an invoice
- Cannot be voided (must refund if needed)
- Invoice ID clickable (links to invoice details)
- Status shows checkmark (✓)
- Cannot be modified
Invoice Generation:
When you generate an invoice for a customer:
- System finds all uninvoiced transactions for that customer
- Optionally filter by date range
- Transactions included in new invoice
- Transaction
invoice_idfield populated - Transaction now marked as "invoiced"
See payments_invoices for invoice generation details.
Common Workflows
Workflow 1: Manual Credit for Service Outage
- Customer calls: "Service was down for 2 days"
- Staff decides to credit £10
- Navigate to customer Billing tab
- Click "+ Add Transaction"
- Select Credit transaction type
- Select Cash Payment credit type
- Enter title: "Service Outage Credit"
- Enter description: "Compensation for 2-day outage 8-9 Jan"
- Enter retail cost: 10.00
- Select affected service from dropdown
- Click "Add Transaction"
- Transaction appears with -£10.00 amount
- Will be included in next invoice as credit
Workflow 2: Manual Installation Fee
- Field tech installs service
- Staff needs to charge £75 installation fee
- Navigate to customer Billing tab
- Click "+ Add Transaction"
- Select Debit transaction type
- Enter title: "Installation Fee"
- Enter description: "Field technician visit for fiber installation"
- Enter retail cost: 75.00
- Enter wholesale cost: 45.00 (optional, for margin tracking)
- Select service installed
- Select site where installed
- Click "Add Transaction"
- Transaction appears in uninvoiced list
- Will be included in next invoice
Workflow 3: Voiding Duplicate Transaction
- Staff notices duplicate transaction
- Verify transaction NOT yet invoiced
- Click actions menu (⋮) on duplicate transaction
- Select "Void Transaction"
- Confirm in modal
- Transaction removed from list
- Uninvoiced total decreases accordingly
Workflow 4: Finding Transactions for Invoice
- Need to generate monthly invoice
- Click Invoice filter: "Not Invoiced"
- Click Apply Filters
- View all uninvoiced transactions
- Note total amount from widgets
- Navigate to generate invoice
- Select date range (e.g., 1-31 Jan)
- Transactions in range included in invoice
Troubleshooting
Cannot void transaction
-
Cause: Transaction already invoiced
-
Fix: Transaction is part of invoice history. If refund needed, create a Credit transaction instead.
-
Cause: Wallet top-up reversal failed (insufficient wallet balance)
-
Fix: Customer already spent the topped-up funds. Use a manual wallet debit/adjustment or financial-docs reversal flows; cannot void the top-up line until the wallet covers the amount.
-
Cause: Card refund failed (Add Funds top-up only)
-
Fix: Wallet reversal is rolled back automatically. Resolve the payment vendor issue and retry void.
Duplicate transactions appearing
- Cause: Service charged multiple times or provisioning error
- Fix: Void the duplicate transaction(s) if not invoiced. If invoiced, issue credit.
Transaction not appearing in list
- Cause: Filters applied or transaction voided
- Fix: Click "Reset Filters" to show all transactions. To see voided transactions, filter by "Void: Void".
Uninvoiced total doesn't match expected
- Cause: Some transactions already invoiced, or voided transactions excluded
- Fix: Apply filter "Invoice: Not Invoiced" to see only uninvoiced. Check voided transactions separately.
Cannot add transaction (customer field disabled)
- Cause: Viewing customer-specific transactions page
- Fix: Customer is pre-selected. If you need to add transaction for different customer, go to system-wide Transactions page.
Related Documentation
payments_invoices- Invoice generation and managementpayments_process- Processing payments against invoicesbasics_payment- Payment methods overviewcsa_activity_log- Viewing transaction history in activity log
Customer Invoices
Transactions </payments_transaction> are grouped together to form an
invoice, which is sent to the customer for payment.
Invoices have a start and end date, which is the period the invoice covers, and a due date, which is the date the invoice is due for payment.

Invoices can be automatically generated by the system, for example, when a service is billed, an invoice is created for the retail cost, or they can be manually created, for example, if a customer requests a copy of an invoice, or if a customer is billed for a one-time charge.
Customer invoices are fully templated with
Mailjet <integrations_mailjet> and can be customized to include the
company logo, address, and payment details, and can be sent to the
customer via email, or downloaded as a PDF.

Customizing Invoice Templates
OmniCRM uses HTML templates with Jinja2 templating to generate invoices. You can fully customize the invoice design, branding, colors, and layout.
Invoice Template Location
Invoice templates are stored in OmniCRM-API/invoice_templates/
Default Templates:
norfone_invoice_template.html- Sample invoice templatecifi_invoice_template.html- Alternative template example
Configuration:
The active invoice template is specified in
OmniCRM-API/crm_config.yaml:
invoice:
template_filename: 'norfone_invoice_template.html'
Available Template Variables
Invoice templates have access to the following Jinja2 variables:
Invoice Information:
{{ invoice_number }}- Unique invoice ID (e.g.,INV-2025-001234){{ date }}- Invoice issue date (ISO format:2025-01-10T12:00:00){{ due_date }}- Payment due date (e.g.,2025-02-10){{ start_date }}- Billing period start date{{ end_date }}- Billing period end date{{ total_amount }}- Total invoice amount before tax (numeric){{ total_tax }}- Total tax amount calculated from all transactions (numeric)
Customer Information:
{{ client.name }}- Customer's full name or company name{{ client.address.address_line_1 }}- Address line 1{{ client.address.address_line_2 }}- Address line 2{{ client.address.city }}- City{{ client.address.state }}- State/province{{ client.address.zip_code }}- Postal/ZIP code{{ client.address.country }}- Country
Transaction Line Items:
Loop through transactions using:
{% for sub_transaction in transactions %}
<tr>
<td>{{ sub_transaction.transaction_id }}</td>
<td>{{ sub_transaction.created.split("T")[0] }}</td>
<td>{{ sub_transaction.title }}</td>
<td>{{ sub_transaction.description }}</td>
<td>${{ "%.2f"|format(sub_transaction.retail_cost) }}</td>
</tr>
{% endfor %}
Transaction Fields:
sub_transaction.transaction_id- Transaction IDsub_transaction.created- Transaction date/timesub_transaction.title- Transaction titlesub_transaction.description- Detailed descriptionsub_transaction.retail_cost- Line item amountsub_transaction.tax_percentage- Tax percentage applied (e.g., 10 for 10%)sub_transaction.tax_amount- Calculated tax amount in dollars
Displaying Tax in Templates:
<td>
{% if sub_transaction.tax_amount and sub_transaction.tax_amount > 0 %}
${{ "%.2f"|format(sub_transaction.tax_amount) }} ({{ sub_transaction.tax_percentage }}%)
{% else %}
-
{% endif %}
</td>
Creating a Custom Invoice Template
Step 1: Copy Existing Template
cd OmniCRM-API/invoice_templates/
cp norfone_invoice_template.html your_company_invoice_template.html
Step 2: Customize HTML/CSS
Edit your_company_invoice_template.html to match your branding:
Key Customization Areas:
-
Company Logo and Branding
<!-- Replace with your logo URL -->

<!-- Update company name -->
<h1>Your Company Name</h1> -
Color Scheme
<style>
/* Primary brand color */
.navbar {
background: linear-gradient(to bottom right, #your-color-1, #your-color-2);
}
/* Table headers */
.table thead th {
background-color: #your-brand-color !important;
color: white !important;
}
/* Buttons and links */
.btn-primary {
background-color: #your-brand-color;
}
</style> -
Company Information Footer
<footer>
<p>Your Company Name</p>
<p>123 Business Street, City, Country</p>
<p>Phone: +1-555-123-4567 | Email: billing@yourcompany.com</p>
<p>ABN/Tax ID: 12345678900</p>
</footer> -
Payment Instructions
<div class="payment-info">
<h3>Payment Methods</h3>
<p><strong>Online:</strong> Pay at https://yourcompany.com/pay</p>
<p><strong>Bank Transfer:</strong></p>
<ul>
<li>Account Name: Your Company Ltd</li>
<li>BSB: 123-456</li>
<li>Account Number: 987654321</li>
<li>Reference: {{ invoice_number }}</li>
</ul>
</div> -
Terms and Conditions
<div class="terms">
<h4>Payment Terms</h4>
<p>Payment due within 30 days of invoice date.</p>
<p>Late payment fees: 2% per month on overdue balances.</p>
<p>For billing inquiries: billing@yourcompany.com</p>
</div>
Step 3: Update Configuration
Edit OmniCRM-API/crm_config.yaml:
invoice:
template_filename: 'your_company_invoice_template.html'
Step 4: Restart API
cd OmniCRM-API
sudo systemctl restart omnicrm-api
Step 5: Test Invoice Generation
- Navigate to a customer with transactions
- Generate a test invoice
- Download PDF to verify formatting
- Email invoice to yourself to test email delivery
Advanced Customization
Conditional Content:
Use Jinja2 conditionals to show/hide content:
{% if total_amount > 1000 %}
<div class="high-value-notice">
<p><strong>Note:</strong> Large balance - Payment plan available upon request.</p>
</div>
{% endif %}
{% if client.address.country == "Australia" %}
<p>GST Included: ${{ "%.2f"|format(total_amount * 0.10) }}</p>
{% endif %}
Multi-Language Support:
Create language-specific templates:
invoice_template_en.html
invoice_template_es.html
invoice_template_fr.html
Configure based on customer's language preference.
Custom Calculations:
<!-- Display subtotal and tax breakdown -->
<tr>
<td colspan="4" class="text-right"><strong>Subtotal:</strong></td>
<td>${{ "%.2f"|format(total_amount) }}</td>
</tr>
<tr>
<td colspan="4" class="text-right"><strong>Tax:</strong></td>
<td>${{ "%.2f"|format(total_tax) }}</td>
</tr>
<tr>
<td colspan="4" class="text-right"><strong>Total:</strong></td>
<td>${{ "%.2f"|format(total_amount + total_tax) }}</td>
</tr>
Note: The total_tax variable is automatically calculated by
summing the tax_amount from all transactions in the invoice. Each
transaction's tax is calculated based on its tax_percentage field,
which defaults to the product's tax_percentage or 0% if not specified.
QR Code for Payment:
Generate QR code for mobile payment:
<div class="qr-payment">

<p>Scan with your phone to pay instantly</p>
</div>
PDF Styling Best Practices
OmniCRM uses WeasyPrint to convert HTML to PDF. Follow these guidelines:
Supported CSS:
- Most CSS 2.1 properties
- Limited CSS3 (flexbox, some transforms)
- Web fonts via
@font-face
Not Supported:
- JavaScript
- CSS Grid (use tables instead)
- Complex animations
- Some modern CSS properties
Page Size and Margins:
@page {
size: A4;
margin: 1cm;
}
body {
font-family: Arial, sans-serif;
font-size: 10pt;
}
Print-Specific Styling:
@media print {
.no-print {
display: none;
}
.page-break {
page-break-after: always;
}
}
Table Layout:
.table {
table-layout: fixed;
width: 100%;
}
.table th, .table td {
word-wrap: break-word;
padding: 4px;
}
Font Embedding:
For custom fonts, use web-safe fonts or embed:
@font-face {
font-family: 'YourFont';
src: url('https://yourcompany.com/fonts/yourfont.woff2') format('woff2');
}
body {
font-family: 'YourFont', Arial, sans-serif;
}
Testing Invoice Templates
Test Checklist:
- Visual Inspection:
- Logo displays correctly
- Colors match brand guidelines
- Text is readable (not too small)
- Tables align properly
- All sections present
- Data Accuracy:
- Customer details correct
- Transaction amounts sum correctly
- Dates formatted properly
- All variables substituting correctly
- PDF Quality:
- File size reasonable (<5MB)
- Images sharp and clear
- No text cutoff or overflow
- Page breaks in appropriate places
- Multi-Page Invoices:
- Headers repeat on each page
- Page numbers display
- Long transaction lists paginate correctly
- Email Delivery:
- PDF attaches to email
- File size under Mailjet limit (15MB)
- Renders in Gmail, Outlook, Apple Mail
Test Command (Manual Generation):
You can test invoice generation via API:
curl -X GET "http://localhost:5000/crm/invoice/{invoice_id}/pdf" \
-H "Authorization: Bearer YOUR_TOKEN" \
--output test_invoice.pdf
Common Template Issues
Variables not substituting:
- Cause: Typo in variable name or missing data
- Fix: Check spelling exactly (case-sensitive), verify data exists in database
PDF styling broken:
- Cause: Unsupported CSS property
- Fix: Use CSS 2.1 properties, test with WeasyPrint-compatible CSS
Images not showing:
- Cause: Relative URLs or blocked external resources
- Fix: Use absolute HTTPS URLs, ensure images publicly accessible
Tables overflowing page:
- Cause: Fixed column widths too wide
- Fix: Use percentage widths,
table-layout: fixed
Fonts not rendering:
- Cause: Font not embedded or unavailable
- Fix: Use web-safe fonts (Arial, Times New Roman, etc.) or properly embed custom fonts
PDF generation fails:
- Cause: HTML syntax errors or WeasyPrint crash
- Fix: Validate HTML, check WeasyPrint logs, simplify complex layouts
Invoice PDF Caching
To improve performance and reduce redundant PDF generation, OmniCRM includes an Invoice PDF caching system. When an invoice PDF is first generated, it is cached in the database for subsequent requests.
How PDF Caching Works:
- First Request - When an invoice PDF is requested (download or
email), the system:
- Generates the PDF from the invoice template
- Encodes the PDF as Base64
- Calculates a SHA256 hash of the PDF content
- Stores in
Invoice_PDF_Cachetable with:- Invoice ID reference
- PDF data (Base64-encoded)
- Filename
- Content hash (for integrity verification)
- Creation timestamp
- Subsequent Requests - When the same invoice is requested again:
- System checks for cached PDF by invoice_id
- If cache exists and is valid, returns cached PDF immediately
- Updates
last_accessedtimestamp to track cache usage
- Cache Invalidation - Cached PDFs are invalidated when:
- Invoice is modified (transactions added/removed, details changed)
- Invoice template is updated
- Manual cache clearing is triggered
Benefits:
- Performance - Instant PDF delivery for repeat requests (no regeneration delay)
- Consistency - Same PDF for all downloads of an invoice (unless invoice is modified)
- Server Load - Reduces CPU usage from PDF generation
- User Experience - Loading indicator appears during initial generation, subsequent requests are instant
Cache Management:
The Invoice PDF Cache is automatically managed by the system. Old or unused cache entries can be purged periodically based on:
- Age (e.g., remove cache entries older than 90 days)
- Access patterns (remove entries not accessed in 30 days)
- Storage limits (implement cache size limits if needed)
API Behavior:
When downloading an invoice via API or UI:
- First request: Shows loading indicator while PDF generates, then caches
- Subsequent requests: Immediate download from cache
- Cache hit/miss is transparent to the user
Important: When you update your invoice template, clear the cache to ensure new invoices use the updated design:
-- Clear all cached invoice PDFs (run in MySQL)
DELETE FROM Invoice_PDF_Cache;
Or update crm_config.yaml to automatically invalidate cache on
template change.
Accessing Invoices
Invoices can be viewed at the system level or per-customer:
Per-Customer View:
- Navigate to Customers → [Select Customer]
- Click Billing tab
- View invoices list in the third card
System-Wide View:
- Navigate to Billing → Invoices (from main menu)
- View all invoices across all customers
Invoice Statistics Widgets
At the top of the invoices page, four statistics cards display financial summaries.

Widget Descriptions:
- Total Invoices - Sum of all invoice retail costs (all time) and count of invoices sent
- Unpaid Invoices - Sum of invoices not yet paid and count of unpaid invoices
- Invoices This Month - Sum of invoices created this calendar month with count
- Invoices Last Month - Sum of invoices created last calendar month with count
Value Formatting:
- Values over 1,000: Display as "k" suffix (e.g., $1.5k)
- Values over 1,000,000: Display as "M" suffix (e.g., $2.3M)
- Values over 1,000,000,000: Display as "B" suffix (e.g., $1.1B)
Trend Indicators:
- Widgets for "This Month" and "Last Month" show percentage change
- Green arrow up: Increase from previous period
- Red arrow down: Decrease from previous period
- Gray arrow right: No change
Invoices List
The invoices table displays all invoices with the following columns:

Column Descriptions:
- ID - Unique invoice ID
- Title - Invoice title/description
- Period - Billing period (start date - end date) or "N/A" for one-time invoices
- Due Date - Payment due date
- Created - Invoice creation date
- Amount - Total invoice amount (retail cost)
- Status - Paid, Unpaid, or Refunded
- Actions - Available actions (varies by status)
Action Icons:
- ⬇ (Download) - Download invoice PDF
- 🗑️ (Delete) - Void invoice (only if not paid)
- 💰 (Pay) - Pay invoice online (only if unpaid)
- ✉️ (Email) - Send invoice email to customer
- 💸 (Refund) - Refund Stripe payment (only for paid Stripe invoices)
Generating an Invoice
Click "+ Generate Proforma Invoice" to create a new invoice.

Field Descriptions:
- Search Customers - Select customer (only shown in system-wide view, pre-filled in customer view)
- Title - Invoice title/name (optional, defaults to "Invoice for [Period]")
- Start Date - Beginning of billing period (defaults to 14 days ago)
- End Date - End of billing period (defaults to today)
- Due Date - Payment deadline (defaults to today)
- Transaction Preview - Shows all uninvoiced transactions in date range with ability to include/exclude specific transactions
Transaction Selection:
- ✓ (Green Plus) - Click to exclude a transaction from the invoice
- × (Red X) - Click to include a previously excluded transaction
- Select All - Include all displayed transactions
- Clear All - Exclude all transactions
- Excluded transactions appear grayed out with strikethrough text
- Real-time totals update as you select/deselect transactions
What Happens:
- System finds all uninvoiced transactions for customer within date range
- Displays transaction preview with ability to include/exclude individual transactions
- Shows real-time calculation of subtotal, tax, and total based on selected transactions
- Only selected (included) transactions are added to the invoice
- Generates invoice PDF and caches it
- Marks selected transactions as invoiced (
invoice_idfield populated) - Excluded transactions remain uninvoiced and available for future invoices
- Invoice appears in list with "Unpaid" status
Example Use Cases:
Monthly Billing: Set start date to first of month, end date to last day of month, preview shows all uninvoiced transactions from that period. Select all or manually exclude specific ones.
Service-Specific Invoice: Use same date range, then manually exclude unwanted transactions (e.g., exclude non-mobile transactions to create mobile-only invoice).
One-Time Invoice: Set both start and end date to the same day, preview shows only transactions from that date. Exclude any charges not relevant to this specific invoice.
Viewing Invoice Details
Click on any invoice row in the table to view full invoice details including all transactions, totals, and available actions.

Invoice Details Modal:
- Invoice Information - Shows invoice ID, title, dates, payment status, and void status
- Transactions List - Displays all transactions included in the
invoice with:
- Transaction date
- Title and description
- Retail cost
- Tax amount and percentage (formatted as
$10.00 (10%)) - Tax-exempt transactions show "-" in Tax column
- Totals Summary - Real-time calculation showing:
- Transaction count
- Subtotal (sum of all retail costs)
- Tax (sum of all tax amounts)
- Invoice Total (subtotal + tax)
- Action Buttons - Same actions available as in the table:
- Download PDF - Download invoice PDF (always available)
- Send Email - Email invoice to customer (non-voided invoices)
- Pay Invoice - Process payment (unpaid, non-voided invoices only)
- Refund - Refund Stripe payment (paid Stripe invoices only)
- Delete - Void invoice (unpaid, non-voided invoices only)
Downloading Invoice PDFs
Click the download icon (⬇) in the table or "Download PDF" button in the invoice details modal to download an invoice as PDF.
Download Process:
- Click download icon next to invoice
- Loading spinner appears during generation (first time only)
- Browser prompts to save file:
Invoice_01234.pdf - PDF opens or saves to Downloads folder
PDF Caching Behavior:
- First Download - PDF generated from template, cached in database (may take 2-3 seconds)
- Subsequent Downloads - Instant download from cache
- Cache Invalidation - Cache cleared if invoice modified or template updated
Troubleshooting Download Issues:
- Spinner never stops - Check browser console, API may be down
- PDF blank or corrupted - Check invoice template for syntax errors
- Download fails - Check popup blocker settings, try different browser
Paying Invoices
Click the pay icon (💰) to pay an invoice online.

Payment Process:
- Click pay icon on unpaid invoice
- Payment modal opens showing invoice details
- Select payment method:
- Stripe Transaction - Charge saved credit card (available to all users)
- Cash - Manual cash payment (staff only)
- Refund - Apply refund as payment (staff only)
- POS Transaction - Point-of-sale terminal (staff only)
- Bank Transfer - Manual bank transfer (staff only)
- If Stripe selected:
- Select card from saved payment methods
- Default card pre-selected
- Click to select different card
- If other method selected:
- Enter reference number (optional)
- Click "Pay Invoice" to process
- System processes payment:
- Stripe - Charges card via Stripe API
- Other methods - Creates negative transaction for payment amount
- Invoice status changes to "Paid"
- Success notification displayed
Self-Care vs Staff Payment:
:doc:`Self-Care Portal <self_care_portal>` (Customers):
- Only Stripe payment available
- Must have saved payment method
- Warning shown if no payment methods exist
- Link to add payment method provided
Staff Portal (Admins):
- All payment methods available
- Can mark invoice paid manually (cash, POS, bank transfer)
- Can enter reference numbers for tracking
Payment Method Warning:
If customer has no saved payment methods, a warning is displayed prompting them to add a payment method before they can pay invoices.

Emailing Invoices
Click the email icon (✉️) to send invoice to customer.
What Happens:
- Click email icon next to invoice
- System retrieves invoice PDF from cache (or generates if not cached)
- Sends email via
Mailjet <integrations_mailjet>usingapi_crmCommunicationCustomerInvoicetemplate - Email includes:
- Invoice PDF as attachment
- Customer name
- Invoice number and due date
- Total amount due
- Link to pay invoice online
- Link to view/download invoice
- Success notification: "Invoice email successfully sent"
Email Recipients:
Email sent to all customer contacts with type "billing" or primary contact if no billing contact exists.
Email Template Variables:
{{ var:customer_name }}- Customer's full name{{ var:invoice_number }}- Invoice ID{{ var:invoice_date }}- Invoice issue date{{ var:due_date }}- Payment due date{{ var:total_amount }}- Total amount due{{ var:invoice_url }}- Link to view/download PDF{{ var:pay_url }}- Link to pay invoice online
Troubleshooting Email Issues:
- Email not sent - Check Mailjet API credentials in
crm_config.yaml - Customer not receiving - Verify customer contact email addresses
- PDF not attaching - Check PDF generation succeeded (try downloading first)
Voiding Invoices
Click the delete icon (🗑️) to void an invoice.
Requirements:
- Invoice must be Unpaid
- Paid invoices cannot be voided (must be refunded instead)
How to Void:
- Locate unpaid invoice in list
- Click delete icon (🗑️)
- Confirm in modal:

What Happens:
- Invoice marked as
void = true - All transactions unlinked from invoice (
invoice_idset to null) - Transactions become "uninvoiced" again
- Transactions can be included in new invoice
- Invoice appears in list with "Void:" prefix in title
- Invoice actions disabled (no download, pay, or email)
- Can be viewed by filtering for "Void" invoices
Important Notes:
- Voiding is NOT the same as refunding
- Void = "This invoice should never have existed" (billing error, duplicate)
- Refund = "Reverse a valid paid invoice" (return money to customer)
Refunding Invoices
Click the refund icon (💸) to refund a paid invoice.
Requirements:
- Invoice must be Paid
- Invoice must be paid via Stripe
- Invoice must have a valid
payment_reference(Stripe payment intent ID) - Only available to staff users (not Self-Care)
How to Refund:
- Locate paid Stripe invoice
- Click refund icon (💸)
- Refund confirmation modal opens:

- Click "Confirm Refund"
- System processes Stripe refund:
- Calls Stripe API to refund payment
- Creates refund transaction in Stripe
- Updates invoice with
refund_reference
- Invoice status changes to "Refunded"
- Success notification displayed
What Happens After Refund:
- Invoice remains in system (not voided)
- Status shows "Refunded"
- Transactions remain linked to invoice
- Customer receives refund to original payment method (3-7 business days)
- Stripe dashboard shows refund transaction
Refund Restrictions:
- Cannot refund invoices paid via cash, POS, or bank transfer (manual reversal required)
- Cannot partial refund (full invoice amount only)
- Cannot refund twice
Searching and Filtering Invoices
Search
Use the search bar to find invoices. Searches across:
- Invoice ID
- Invoice title
- Customer name (system-wide view only)
Filters
Apply filters to narrow invoice list:
Available Filters:
- Void Status - All, Void, Not Void
- Paid Status - All, Paid, Not yet Paid
Filter Actions:
- Apply Filters - Apply selected filters to list
- Reset Filters - Clear all filters and show all invoices
Sorting
Click any column header to sort:
- ID - Sort by invoice ID (newest/oldest)
- Title - Sort alphabetically
- Due Date - Sort by due date
- Created - Sort by creation date
- Amount - Sort by retail cost (highest/lowest)
- Status - Sort by paid status (paid first or unpaid first)
Click again to reverse sort direction (ascending ↔ descending).
Pagination
Navigate through large invoice lists with page controls showing current page, total pages, and items per page selector (10, 25, 50, or 100 items).
Common Invoice Workflows
Workflow 1: Monthly Billing with Transaction Preview
- End of month arrives (e.g., January 31)
- Navigate to Billing → Invoices
- Click "+ Generate Proforma Invoice"
- Select customer (or do per-customer if billing many customers)
- Set dates:
- Start Date: 2025-01-01
- End Date: 2025-01-31
- Due Date: 2025-02-15 (15 days from now)
- Title: "January 2025 Services" (optional)
- Transaction Preview section appears showing all uninvoiced transactions from January
- Review the preview:
- All transactions are included by default
- Check totals: Subtotal, Tax, and Invoice Total
- Verify all charges are correct
- Click "Generate Invoice" (button shows transaction count, e.g., "Generate Invoice (15)")
- Invoice created with all selected transactions
- Click invoice row to view details and verify
- Click "Send Email" button in details modal or email icon in table
- Customer receives invoice email with PDF and pay link
Workflow 2: Selective Transaction Invoicing
- Customer has multiple services (Mobile + Internet) and misc charges
- Wants separate invoices for each service
- Generate first invoice (Mobile Services):
- Click "+ Generate Proforma Invoice"
- Title: "Mobile Services - January 2025"
- Start/End: Jan 1-31
- Due Date: Feb 15
- In transaction preview, exclude all non-mobile transactions:
- Click X button next to Internet transactions
- Click X button next to miscellaneous charges
- Only Mobile service transactions remain selected
- Verify totals reflect only mobile services
- Click "Generate Invoice" (shows count of mobile transactions)
- Generate second invoice (Internet Services):
- Click "+ Generate Proforma Invoice" again
- Title: "Internet Services - January 2025"
- Start/End: Jan 1-31 (same period)
- In transaction preview:
- Mobile transactions already invoiced (don't appear)
- Exclude miscellaneous charges using X button
- Only Internet service transactions remain
- Click "Generate Invoice"
- Generate third invoice (Additional Charges):
- Click "+ Generate Proforma Invoice" again
- Title: "Additional Charges - January 2025"
- Only uninvoiced misc charges appear in preview
- Click "Select All" to include all
- Click "Generate Invoice"
- Email all three invoices to customer
Workflow 3: Excluding Disputed or Pending Transactions
- End of billing period arrives
- Navigate to customer Billing tab
- Click "+ Generate Proforma Invoice"
- Set billing period dates
- Transaction preview shows 20 transactions
- Customer has disputed one charge and another is pending investigation
- In transaction preview:
- Locate disputed transaction (e.g., "Data overage charge")
- Click X button to exclude it
- Locate pending transaction (e.g., "Installation fee")
- Click X button to exclude it
- Transaction count updates: "18 Transactions selected"
- Totals recalculate automatically
- Review updated totals (excludes disputed amounts)
- Click "Generate Invoice (18)"
- Invoice generated with only approved transactions
- Disputed/pending transactions remain uninvoiced for next billing cycle
Workflow 4: Quick Invoice Review and Adjustment
- Staff generates monthly invoice
- Transaction preview shows unexpected high total
- Review each transaction in the preview:
- Notice duplicate charge for same service
- Click X to exclude the duplicate
- Notice test transaction that shouldn't be billed
- Click X to exclude test transaction
- Totals update in real-time
- Verify new total matches expected amount
- Click "Generate Invoice" with corrected transactions
- Go back and void/delete the excluded transactions if needed
- Email invoice to customer with confidence
Workflow 5: One-Time Installation Invoice
- Field tech completes installation
- Staff adds installation transaction manually
- Navigate to customer Billing tab
- Click "+ Generate Proforma Invoice"
- Set dates:
- Start Date: today
- End Date: today
- Due Date: today + 7 days
- Title: "Installation Services"
- Transaction preview shows only today's transactions
- Verify installation charge appears
- Exclude any recurring charges using X button (if present)
- Click "Generate Invoice"
- Email to customer immediately
- Customer pays online via Stripe
Workflow 6: Reviewing Invoice Before Customer Contact
- Customer calls with billing question
- Staff navigates to customer's invoice list
- Click on invoice row to open Invoice Details modal
- Review invoice information:
- Invoice ID, dates, status
- All transactions included with descriptions
- Tax breakdown per transaction
- Subtotal, Tax, and Total amounts
- Answer customer's questions with exact details
- If customer requests PDF, click "Download PDF" button in modal
- If customer requests email resend, click "Send Email" button
- Close modal when done
Workflow 7: Correcting Billing Error
- Customer reports incorrect charge
- Staff clicks on invoice row to view details
- Reviews transaction list in Invoice Details modal
- Identifies incorrect transaction
- Invoice is unpaid, so can be voided
- Click "Delete" button in modal footer
- Confirm void
- Transactions become uninvoiced again
- Staff modifies or removes incorrect transaction from transaction list
- Generate new invoice with corrected transactions:
- Use transaction preview to exclude corrected transaction if needed
- Include only valid charges
- Email corrected invoice to customer
Workflow 8: Processing Multiple Payments
- Customer brings cash to pay multiple invoices
- Navigate to customer Billing tab
- View unpaid invoices
- Click on first invoice row to view details
- Verify amount and transactions
- Click "Pay Invoice" button in modal footer
- Select "Cash" payment method
- Enter reference: "Cash paid 2025-01-15"
- Click "Pay Invoice"
- Modal closes, invoice marked as "Paid"
- Repeat for remaining invoices
- All invoices now marked as "Paid"
Workflow 9: Handling Refund Request
- Customer requests refund for overpayment
- Staff verifies invoice was paid via Stripe
- Navigate to invoice in list
- Click on invoice row to view details
- Verify payment information and amount
- Click "Refund" button in modal footer (only appears for Stripe invoices)
- Confirm refund
- System processes Stripe refund
- Invoice status changes to "Refunded"
- Customer receives refund in 3-7 business days
- Staff follows up with customer to confirm receipt
Troubleshooting
Cannot generate invoice - No transactions found
- Cause: No uninvoiced transactions in specified date range
- Fix: Check transaction list, verify transactions exist and are not already invoiced. Adjust date range or remove filter.
Invoice PDF generation fails
- Cause: Template syntax error, WeasyPrint crash, or missing customer data
- Fix: Check invoice template HTML for errors, verify customer address fields populated, review API logs.
Payment fails with Stripe error
- Cause: Card declined, insufficient funds, expired card, or Stripe API issue
- Fix: Try different payment method, verify card valid, check Stripe dashboard for decline reason.
Cannot void invoice
- Cause: Invoice already paid
- Fix: Paid invoices cannot be voided. If refund needed, use refund function for Stripe invoices or create credit transaction manually.
Invoice email not sending
- Cause: Mailjet API credentials invalid, customer has no billing contact, or email template missing
- Fix: Verify Mailjet configuration in
crm_config.yaml, check customer contacts, verify invoice email template exists.
Refund button not appearing
- Cause: Invoice paid via cash/POS/bank transfer (not Stripe), or invoice not paid
- Fix: Refund button only appears for Stripe payments. For other payment methods, create manual credit transaction.
Download PDF shows old template design
- Cause: PDF cached before template update
- Fix: Clear invoice PDF cache:
DELETE FROM Invoice_PDF_Cache WHERE invoice_id = X;
Customer cannot pay invoice (no payment methods)
- Cause: No saved payment methods in Self-Care portal
- Fix: Customer must add credit card at Payment Methods page before paying invoices.
Multiple invoices generated for same period
- Cause: Staff generated invoice twice, or date ranges overlap
- Fix: Void duplicate invoice. Adjust date ranges to prevent overlap. Use transaction preview to ensure unique transaction sets.
Transaction preview shows no transactions
- Cause: All transactions in date range are already invoiced or no transactions exist
- Fix: Verify date range is correct. Check transaction list to confirm transactions exist. Filter invoices to see which invoice contains the transactions.
Cannot exclude transaction from invoice generation
- Cause: Transaction already invoiced or browser issue
- Fix: Verify transaction shows in preview with checkmark. Refresh page and try again. Clear browser cache if issue persists.
Invoice total doesn't match expected amount
- Cause: Unexpected transactions included, tax not calculated, or excluded transactions still counted
- Fix: Review transaction preview carefully. Check each transaction's retail cost and tax. Verify excluded transactions are grayed out. Check transaction count badge on Generate Invoice button.
Generate Invoice button is disabled
- Cause: No transactions selected or invalid date range
- Fix: Ensure at least one transaction is included (not excluded). Verify Start Date is before End Date. Check that Due Date is set.
Invoice Details modal not opening
- Cause: JavaScript error or page not fully loaded
- Fix: Refresh page. Check browser console for errors. Try different browser. Verify internet connection.
Transaction tax not displaying in Invoice Details
- Cause: Transaction has 0% tax or tax_amount is null
- Fix: Verify transaction has tax_percentage set. Check that tax_amount was calculated when transaction was created. Update transaction if needed.
Action buttons missing in Invoice Details modal
- Cause: Invoice is voided or user lacks permissions
- Fix: Voided invoices only show Download PDF button. Verify invoice status. Check user role and permissions.
Related Documentation
integrations_mailjet- Email invoice delivery and templatesadministration_configuration- Invoice template configurationpayments_transaction- Creating transactions that appear on invoicespayments_process- Processing invoice paymentspayment_system_guide- Payment API reference and vendor configuration
Payment Methods Management
OmniCRM's Payment Methods system allows customers and staff to securely manage payment cards using multi-vendor payment processing (Stripe, PayPal, etc.). Payment methods enable automatic billing for services, one-time payments, and recurring charges without storing sensitive card data in OmniCRM.
See also: Payment System Guide <payment_system_guide>,
Billing Overview <billing_overview>,
Payment Processing <payments_process>, Invoices <payments_invoices>.
Overview
The payment methods system provides:
- Secure Card Storage - Cards tokenized by payment vendors (Stripe, PayPal), never stored in OmniCRM
- Multi-Vendor Support - Stripe and PayPal payment methods supported
- Multiple Cards - Customers can store multiple payment methods
- Default Selection - Designate preferred payment method for automatic charges
- Expiry Tracking - Monitor and update expiring cards
- Self-Service - Customers can manage their own cards via
Self-Care Portal <self_care_portal> - Staff Management - Support staff can add/remove cards on behalf of customers
Supported Payment Methods:
- Credit Cards (Visa, Mastercard, American Express, Discover)
- Debit Cards
- Prepaid Cards (if supported by card network)
Not Stored in OmniCRM:
Card details are tokenized by payment vendors and stored securely. OmniCRM only stores:
- Payment vendor (stripe, paypal)
- Card brand (Visa, Mastercard, etc.)
- Last 4 digits
- Expiry month/year
- Cardholder name/nickname
- Vendor-specific payment method token
Accessing Payment Methods
From Customer Page:
- Navigate to Customers → [Select Customer]
- Click Billing tab
- Scroll to Payment Methods section
Or directly:
From Expiring Cards Dashboard:
View all customers with expiring cards:
This shows a system-wide list of cards expiring within the next 60 days.
Payment Methods List
The payment methods table displays all stored cards for a customer:

Column Descriptions:
- Nickname - Friendly name for the card (e.g., "Personal Card", "Work Visa")
- Issuer - Card brand and last 4 digits
- Expiry - Expiration month/year (MM/YYYY format)
- Added - Date card was added to account
- Default - Checkmark indicates default payment method for automatic charges
Actions Per Card:
Each row has an actions menu (⋮) with options:
- Set as Default - Make this the default payment method
- Delete - Remove card from account
Adding a Payment Method
Click "Add Payment Method" to open the secure payment modal.
Step 1: Enter Card Details
The secure payment form appears (powered by Stripe Elements or PayPal SDK):

Required Fields:
- Card Information - Card number, expiry, CVC (validated by Stripe)
- Cardholder Name - Name on the card
- Country/Region - Billing country
Optional Fields:
- Card Nickname - Friendly label to distinguish between cards
Security:
- Card details entered directly into vendor-hosted secure iframe (Stripe Elements / PayPal SDK)
- OmniCRM never sees or stores full card numbers
- PCI DSS compliance handled by payment vendor
- Real-time validation prevents invalid card numbers
Step 2: Submit and Tokenize
When you click "Add Payment Method":
- Client-Side Validation:
- Payment vendor validates card number format
- Checks expiry date is in the future
- Verifies CVC format
- Tokenization:
- Card details sent directly to payment vendor (not OmniCRM)
- Vendor creates a secure token (e.g.,
pm_1A2B3C4Dfor Stripe) - Token returned to OmniCRM
- Server Processing:
- OmniCRM saves token to customer record with vendor identifier
- Stores last 4 digits, brand, expiry, and vendor name for display
- No full card number ever touches OmniCRM servers
Step 3: Confirmation
Success message appears:
Your Visa ending in 1234 has been added to your account.
The new card appears in the payment methods table.
Automatic Default Selection:
- If this is the customer's first card, it's automatically set as default
- If customer already has cards, new card is added as non-default
- Customer can change default after adding
Setting Default Payment Method
The default payment method is used for:
- Automatic recurring service charges
- Invoice payments
- Top-ups and recharges
- One-time transactions (unless specified otherwise)
To Change Default:
-
Locate the card you want to set as default in the payment methods table
-
Click the actions menu (⋮) next to the card
-
Select "Set as Default"
-
Confirmation appears
Visa ending in 5678 is now your default payment method.
The checkmark moves to the newly selected card.
Visual Indicator:
Default cards show:
in the Default column, typically with a green checkmark badge.
Deleting a Payment Method
Remove cards that are expired, lost, or no longer needed.
Step 1: Initiate Deletion
- Find the card to delete in the payment methods table
- Click the actions menu (⋮)
- Select "Delete"
Step 2: Confirm Deletion
A confirmation modal appears:
Are you sure you want to delete this payment method?
Card: Visa ending in 1234 Expiry: 12/2026
⚠️ Warning: If this is your only payment method, you will need to add a new one to continue using services that require automatic billing.
[Cancel] [Delete Payment Method]
Click "Delete Payment Method" to confirm.
Step 3: Deletion Complete
Success message:
The card is removed from the table and deleted from Stripe.
Important Restrictions:
- Cannot delete default if other cards exist - Set a different card as default first
- Warning if deleting last card - Services requiring payment may be suspended
- No undo - Deletion is permanent; customer must re-add card if needed
Managing Expiring Cards
OmniCRM tracks card expiry dates and provides tools to proactively update expiring cards.
Expiring Cards Dashboard
Navigate to Billing → Expiring Cards to see a system-wide list:
Customer Card Expiry Days Until Action John Smith Visa **1234 02/2025 12 days Update Acme Corp MC5678 03/2025 45 days Update Jane Doe Amex**9012 01/2025 EXPIRED Update

Filters:
- Expiry Range - Next 30/60/90 days or already expired
- Customer Type - Individual vs Business
- Service Type - Filter by service requiring payment method
Actions:
- Update - Opens customer's payment methods page to add new card
- Notify - Send email reminder to customer (if Mailjet configured)
Expiry Notifications
If Mailjet is configured, automatic emails are sent:
- 60 days before expiry - First reminder
- 30 days before expiry - Second reminder
- 7 days before expiry - Final warning
- At expiry - Card has expired notice
Customers can click a link in the email to update their payment method via the Self-Care portal.
Email Template Variables:
Mailjet templates receive:
- Customer name
- Card brand and last 4 digits
- Expiry date
- Link to Self-Care payment methods page
See integrations_mailjet for email template configuration.
Updating an Expiring Card
Recommended Workflow:
- Customer receives expiry notification email
- Customer logs into Self-Care portal
- Navigates to Billing → Payment Methods
- Clicks "Add Payment Method"
- Enters new card details (same card with updated expiry, or replacement card)
- Sets new card as default
- Deletes old/expired card
Staff Workflow:
If customer calls support:
- Staff opens customer account
- Navigates to Billing → Payment Methods
- Adds new card on customer's behalf (customer provides details over phone)
- Sets new card as default
- Deletes expired card
- Confirms with customer
Warning
Never ask customers to email or text card details. Always use:
- Secure Self-Care portal for self-service
- Phone with staff entering details directly into system
- In-person at retail location
What Happens When Cards Expire
When a payment card reaches its expiry date and is not updated:
Immediate Effects:
- Automatic Payments Fail
- Payment vendor rejects transactions with expired cards
- Monthly service renewals fail to process
- Auto-top-ups fail
- Invoice auto-payments fail
- Customer Notifications
- System attempts to charge card
- Payment failure notification sent
- "Update Payment Method" email sent with link to Self-Care portal
- Service Status Changes
- Postpaid Services - May continue temporarily with outstanding balance
- Prepaid Services - Service suspension when balance depletes
- Auto-Renew Services - Renewal fails, service may expire
Subsequent Actions:
Day 1-3 (Grace Period):
- Service continues normally
- Customer receives first payment failure notice
- System attempts retry (depending on configuration)
Day 4-7:
- Second payment attempt (if configured)
- Warning email sent
- Customer service may contact customer
Day 8-14:
- Service may be suspended for non-payment
- Suspended status prevents usage but preserves account
- Customer can restore by updating payment method and paying outstanding balance
Day 15+:
- Service may be terminated for non-payment
- Inventory (SIM cards, equipment) marked for return
- Final notice sent
- Account referred to collections (if applicable)
Preventing Service Interruption:
To avoid service disruption:
- Update cards 30 days before expiry
- Add multiple payment methods for redundancy
- Enable payment failure alerts
- Monitor Expiring Cards dashboard weekly
Restoring Service After Expiry:
If service suspended due to expired card:
- Add new valid payment method
- Set as default
- Pay outstanding balance (if any)
- Contact support to reactivate service
- Service restored within minutes to hours
Payment Method Security
Tokenization
OmniCRM uses vendor tokenization to ensure security:
- Customer enters card → Sent directly to payment vendor servers
- Vendor validates and tokenizes → Creates unique token
- Token stored in OmniCRM → Full card number never stored
- Payment processing → Token sent to vendor, vendor charges card
What OmniCRM Stores:
{
"vendor": "stripe",
"vendor_payment_method_id": "pm_1A2B3C4D5E6F",
"payment_type": "card",
"brand": "visa",
"last4": "1234",
"exp_month": 12,
"exp_year": 2026,
"name": "John Smith",
"nickname": "Personal Card",
"is_default": true
}
What OmniCRM Does NOT Store:
- Full card number
- CVV/CVC code
- Magnetic stripe data
- PIN numbers
PCI Compliance
By using vendor-hosted payment forms:
- Reduced PCI scope - Card data never touches OmniCRM servers
- Vendor-hosted fields - Card entry happens in vendor's secure iframe
- No card storage - Tokens used instead of raw card data
- Secure transmission - All communication over HTTPS/TLS
See Payment System Guide <payment_system_guide> for payment vendor security details.
Common Workflows
Workflow 1: Customer Adds First Payment Method
Scenario: New customer signing up for service
- Customer creates account
- Selects service plan
- Prompted to add payment method during checkout
- Enters card details in Stripe modal
- Card tokenized and saved
- Automatically set as default
- Service provisioned
- First charge processed
Workflow 2: Customer Updates Expiring Card
Scenario: Credit card about to expire
- Customer receives email notification (60 days before expiry)
- Logs into Self-Care portal
- Navigates to Billing → Payment Methods
- Reviews current card expiring 12/2025
- Clicks "Add Payment Method"
- Enters replacement card with expiry 12/2028
- Sets new card as default
- Deletes old card
- Confirmation email sent
Workflow 3: Staff Helps Customer Over Phone
Scenario: Customer calls: "My card was declined"
- Customer calls support
- Staff verifies identity (security questions)
- Staff checks payment methods: Card expired 01/2025
- Staff: "Your card has expired. Do you have a new card?"
- Customer provides new card details over phone
- Staff navigates to Customers → [Customer] → Billing
- Clicks "Add Payment Method"
- Enters card details as customer reads them
- Sets new card as default
- Deletes expired card
- Retries failed payment
- Confirms with customer: "Payment successful, service restored"
Workflow 4: Business Customer with Multiple Cards
Scenario: Company wants different cards for different purposes
- Business customer adds primary card (Visa ending 1111)
- Sets as default for monthly service charges
- Adds backup card (Mastercard ending 2222) for top-ups
- Adds purchasing card (Amex ending 3333) for equipment purchases
- When making top-up, selects Mastercard manually at checkout
- Default Visa still used for automatic monthly billing
Workflow 5: Managing Expiring Cards (Admin)
Scenario: Proactive expiry management
- Admin navigates to Billing → Expiring Cards
- Filters: "Next 30 days"
- Sees 15 customers with expiring cards
- Selects all → "Send Reminder Emails"
- Mailjet sends personalized emails to each customer
- Customers update cards via Self-Care
- Admin reviews list 1 week later
- Calls remaining customers who haven't updated
- Assists with card updates over phone
Troubleshooting
"Card declined" when adding payment method
- Cause: Stripe rejected card (insufficient funds, fraud prevention, issuer decline)
- Fix:
- Try a different card
- Contact card issuer to authorize transaction
- Ensure card supports online purchases
- Check billing address matches card on file
"Error adding payment method" (generic error)
- Cause: Payment vendor API error or network issue
- Fix:
- Refresh page and try again
- Check internet connection
- Verify payment vendor configuration is correct in system settings
- Check browser console for specific error message
- Try different browser (disable ad blockers)
Cannot delete payment method (button disabled)
- Cause: Trying to delete the default card, or it's the only card
- Fix:
- Set a different card as default first
- If it's the only card, add a new card before deleting
Card shows as expired but not in "Expiring Cards" list
- Cause: Card expired recently, cache not refreshed
- Fix:
- Refresh the page
- Check filters on Expiring Cards dashboard
- Expired cards may move to different view
New card not appearing immediately
- Cause: Page hasn't refreshed after adding card
- Fix:
- Payment methods table should auto-refresh
- If not, manually refresh browser
- Check if error occurred during add process
Payment modal won't load
- Cause: Payment vendor SDK not loading, API key issue, or browser extension blocking
- Fix:
- Check browser console for errors
- Disable ad blockers and tracking protection
- Verify payment vendor configuration in system settings
- Ensure vendor SDK script loads (check Network tab)
- Try incognito/private browsing mode
Customer doesn't receive expiry notifications
- Cause: Mailjet not configured or email template missing
- Fix:
- Verify Mailjet credentials in crm_config.yaml
- Check email template exists for card expiry
- Confirm customer email address is valid
- Check Mailjet logs for delivery failures
Best Practices
For Customers:
- Add payment method before service activation to avoid delays
- Keep at least 2 cards on file for redundancy
- Update expiring cards 30+ days before expiry
- Delete old/expired cards to avoid confusion
- Use descriptive nicknames ("Personal Visa", "Work Amex")
- Verify default payment method is correct for automatic billing
For Support Staff:
- Verify customer identity before accessing payment methods
- Never ask customers to send card details via email/SMS/chat
- Process card additions immediately during calls (don't defer)
- Confirm new card is set as default after adding
- Delete old cards only after confirming new card works
- Test payment after updating expired card (process £0.01 authorization)
For Administrators:
- Monitor Expiring Cards dashboard weekly
- Send reminder emails 60/30/7 days before expiry
- Keep payment vendor test/live keys separate for dev vs production
- Ensure Mailjet templates are configured for expiry notifications
- Review failed payment reports to identify expired cards
- Train staff on secure card handling procedures
Security Best Practices:
- Only use vendor publishable keys (never secret keys in frontend)
- Ensure all payment pages load over HTTPS
- Regularly review payment vendor dashboard for suspicious activity
- Enable vendor fraud prevention rules
- Require CVC for all card-not-present transactions
- Log payment method changes in activity log
Related Documentation
Payment System Guide <payment_system_guide>- Payment vendor integration setup and configurationpayments_process- Processing payments with stored payment methodspayments_invoices- Automatic invoice payment using default cardfeatures_topup_recharge- Top-up system using payment methodsbasics_payment- General payment and billing conceptscustomer_care- Self-Care portal for customers to manage their own cards

Process Payments
The majority of payments will be processed automatically by the system, but there are times when you may need to process a payment manually.
To pay an invoice, select the unpaid invoice, and click on the "Pay" button.
This will open a payment form, where you can enter the payment method, and click "Submit" to process the payment.
The customer will automatically receive a receipt for the payment, and the invoice will be marked as paid.
For bank transfers, you can enter the Payment reference and the date the payment was made (if different from the current date).

