Skip to main content

Overview

The Invoices module provides comprehensive billing and payment management. Track invoice statuses, monitor due dates, and manage payment collections with integrated client and sales data.

Payment Tracking

Monitor invoice statuses: Paid, Pending, and Overdue

Due Date Management

Automatic tracking of emission and due dates

Client Integration

Link invoices to client records and sales transactions

Financial Reports

Monthly revenue tracking and payment analytics

Factura Model

The Factura model manages all invoice operations:
app/Models/Factura.php
<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Factura extends Model
{
    use HasFactory;

    protected $fillable = [
        'numero_factura',
        'cliente_id',
        'venta_id',
        'concepto',
        'monto',
        'fecha_emision',
        'fecha_vencimiento',
        'estado',
    ];

    protected $casts = [
        'fecha_emision'     => 'date',
        'fecha_vencimiento' => 'date',
    ];

    public function cliente()
    {
        return $this->belongsTo(Cliente::class);
    }

    public function venta()
    {
        return $this->belongsTo(Venta::class);
    }
}

Model Relationships

Each invoice belongs to a client (belongsTo):
public function cliente()
{
    return $this->belongsTo(Cliente::class);
}
Usage Example:
$factura = Factura::find(1);
$cliente = $factura->cliente;
echo $cliente->nombre . ' ' . $cliente->apellido;

Date Casting

The model automatically casts date fields to Carbon instances:
protected $casts = [
    'fecha_emision'     => 'date',
    'fecha_vencimiento' => 'date',
];
This allows easy date manipulation:
$factura = Factura::find(1);

// Access as Carbon instance
echo $factura->fecha_emision->format('d/m/Y');
echo $factura->fecha_vencimiento->diffForHumans();

// Check if overdue
$is_overdue = $factura->fecha_vencimiento->isPast() && $factura->estado !== 'pagada';

Database Schema

The facturas table structure from the migration:
database/migrations/2026_03_03_191710_create_facturas_table.php
Schema::create('facturas', function (Blueprint $table) {
    $table->id();
    $table->string('numero_factura')->unique();
    $table->foreignId('cliente_id')->constrained('clientes')->onDelete('cascade');
    $table->foreignId('venta_id')->nullable()->constrained('ventas')->onDelete('set null');
    $table->string('concepto');
    $table->decimal('monto', 10, 2);
    $table->date('fecha_emision');
    $table->date('fecha_vencimiento');
    $table->enum('estado', ['pagada', 'pendiente', 'vencida'])->default('pendiente');
    $table->timestamps();
});

Table Fields

FieldTypeConstraintsDescription
idbigintPrimary keyUnique invoice identifier
numero_facturastringUniqueInvoice number (e.g., FAC-2024-001)
cliente_idforeignIdRequiredReference to clients table
venta_idforeignIdNullableOptional reference to sales table
conceptostringRequiredInvoice description/concept
montodecimal(10,2)RequiredInvoice amount
fecha_emisiondateRequiredEmission/issue date
fecha_vencimientodateRequiredDue date
estadoenumDefault: ‘pendiente’Payment status
timestampstimestampsAutocreated_at, updated_at

Foreign Key Constraints

Cascade Deletion: When a client is deleted, all their invoices are automatically removed.Set Null: When a sale is deleted, the venta_id in related invoices is set to null, preserving the invoice record.

Payment Statuses

Paid InvoicesInvoices that have been fully paid by the client.
Factura::where('estado', 'pagada')->get();
Dashboard Metrics:
  • Count: 186 invoices
  • Total: $42,300

Invoice View Features

The invoice interface (facturas.blade.php) provides:

Dashboard Cards

Paid

186 invoices $42,300 total

Pending

34 invoices $8,900 pending

Overdue

12 invoices $3,200 in arrears

Total Issued

232 invoices This month

Analytics Charts

Monthly Revenue Chart

Stacked bar chart showing paid vs pending amounts by month
  • Green bars: Paid invoices
  • Yellow bars: Pending invoices

Invoice Status Chart

Doughnut chart displaying status distribution:
  • Paid: 186 (80%)
  • Pending: 34 (15%)
  • Overdue: 12 (5%)

Invoice Management Table

The main invoice table displays:
  • Invoice number (FAC-2024-XXX)
  • Client name
  • Invoice concept/description
  • Amount (formatted currency)
  • Emission date
  • Due date
  • Status badge (color-coded)
  • Action buttons (View, Download PDF)
The interface includes search functionality and status filtering for efficient invoice management.

Usage Examples

Creating a New Invoice

use App\Models\Factura;
use Carbon\Carbon;

$factura = Factura::create([
    'numero_factura' => 'FAC-2024-006',
    'cliente_id' => 1,
    'venta_id' => 5,
    'concepto' => 'Laptop Pro x1',
    'monto' => 1500.00,
    'fecha_emision' => Carbon::now(),
    'fecha_vencimiento' => Carbon::now()->addDays(15),
    'estado' => 'pendiente'
]);
// Get all invoices with client and sale data
$facturas = Factura::with(['cliente', 'venta'])->get();

foreach ($facturas as $factura) {
    echo $factura->numero_factura;
    echo $factura->cliente->nombre;
    if ($factura->venta) {
        echo $factura->venta->numero_orden;
    }
}

Marking Invoice as Paid

$factura = Factura::find(1);
$factura->estado = 'pagada';
$factura->save();

Finding Overdue Invoices

use Carbon\Carbon;

// Automatically mark overdue invoices
$overdue = Factura::where('estado', 'pendiente')
    ->where('fecha_vencimiento', '<', Carbon::now())
    ->update(['estado' => 'vencida']);

Client Invoice Summary

$cliente_id = 1;

$total_pagadas = Factura::where('cliente_id', $cliente_id)
    ->where('estado', 'pagada')
    ->sum('monto');

$total_pendiente = Factura::where('cliente_id', $cliente_id)
    ->whereIn('estado', ['pendiente', 'vencida'])
    ->sum('monto');

Monthly Revenue Report

use Carbon\Carbon;

$mes_actual = Carbon::now()->month;

$ingresos = Factura::whereMonth('fecha_emision', $mes_actual)
    ->where('estado', 'pagada')
    ->sum('monto');

$pendiente = Factura::whereMonth('fecha_emision', $mes_actual)
    ->where('estado', 'pendiente')
    ->sum('monto');

Invoices Due This Week

use Carbon\Carbon;

$facturas_vencer = Factura::where('estado', 'pendiente')
    ->whereBetween('fecha_vencimiento', [
        Carbon::now(),
        Carbon::now()->addWeek()
    ])
    ->with('cliente')
    ->get();

Key Features

Unique Invoice Numbers

Each invoice has a unique identifier (FAC-2024-XXX)

Client Integration

Direct relationship with client records

Optional Sales Link

Nullable foreign key to sales table

Decimal Precision

Amounts stored with 2 decimal precision

Date Casting

Automatic Carbon instance conversion for dates

Three Payment States

Paid, Pending, and Overdue status tracking

Cascade Deletion

Auto-delete when client is removed

Set Null on Sale Delete

Preserve invoice when sale is deleted

Timestamp Tracking

Automatic created_at and updated_at timestamps

Best Practices

Automatic Status Updates: Consider implementing a scheduled task to automatically update pending invoices to ‘vencida’ when they pass their due date.Payment Reminders: Send automated reminders to clients with pending invoices approaching their due date.PDF Generation: Integrate PDF generation for downloadable invoice documents.

Build docs developers (and LLMs) love