Saltar al contenido

En este artículo aprenderemos cómo configurar y trabajar con múltiples conexiones a bases de datos en Laravel, una funcionalidad muy útil para diversos escenarios como arquitecturas multi-tenant, separación de lecturas/escrituras, o cuando necesitamos interactuar con bases de datos legacy.

Configuración Inicial

1. Variables de Entorno

Primero necesitamos configurar las conexiones en nuestro archivo .env:

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=mi_app
DB_USERNAME=root
DB_PASSWORD=

DB_SECOND_CONNECTION=mysql
DB_SECOND_HOST=127.0.0.1
DB_SECOND_PORT=3306
DB_SECOND_DATABASE=segunda_db
DB_SECOND_USERNAME=root
DB_SECOND_PASSWORD=

DB_LEGACY_CONNECTION=sqlsrv
DB_LEGACY_HOST=192.168.1.100
DB_LEGACY_PORT=1433
DB_LEGACY_DATABASE=legacy_db
DB_LEGACY_USERNAME=root
DB_LEGACY_PASSWORD=

2. Configuración en database.php

En config/database.php, definimos las conexiones:

<?php

return [
    'default' => env('DB_CONNECTION', 'mysql'),
    
    'connections' => [
        'mysql' => [
            'driver' => 'mysql',
            'url' => env('DATABASE_URL'),
            'host' => env('DB_HOST', '127.0.0.1'),
            'port' => env('DB_PORT', '3306'),
            'database' => env('DB_DATABASE'),
            'username' => env('DB_USERNAME'),
            'password' => env('DB_PASSWORD', ''),
            'charset' => 'utf8mb4',
            'collation' => 'utf8mb4_unicode_ci',
            'prefix' => '',
            'strict' => true,
            'engine' => null,
        ],
        
        'segunda_db' => [
            'driver' => env('DB_SECOND_CONNECTION', 'mysql'),
            'host' => env('DB_SECOND_HOST', '127.0.0.1'),
            'port' => env('DB_SECOND_PORT', '3306'),
            'database' => env('DB_SECOND_DATABASE'),
            'username' => env('DB_SECOND_USERNAME'),
            'password' => env('DB_SECOND_PASSWORD', ''),
            'charset' => 'utf8mb4',
            'collation' => 'utf8mb4_unicode_ci',
            'prefix' => '',
        ],
        
        'legacy_db' => [
            'driver' => env('DB_LEGACY_CONNECTION', 'sqlsrv'),
            'host' => env('DB_LEGACY_HOST', 'localhost'),
            'port' => env('DB_LEGACY_PORT', '1433'),
            'database' => env('DB_LEGACY_DATABASE'),
            'username' => env('DB_LEGACY_USERNAME'),
            'password' => env('DB_LEGACY_PASSWORD', ''),
            'charset' => 'utf8',
            'prefix' => '',
        ],
    ],
];

Formas de Uso

1. Usando la Fachada DB

La forma más directa de cambiar entre conexiones es usando la fachada DB:

<?php

// Usando la conexión por defecto
$users = DB::table('users')->get();

// Usando la segunda conexión
$products = DB::connection('segunda_db')->table('products')->get();

// Usando la conexión legacy
$oldOrders = DB::connection('legacy_db')->table('orders')->get();

2. A nivel de Modelo

Puedes especificar una conexión diferente para un modelo específico:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class LegacyOrder extends Model
{
    protected $connection = 'legacy_db';
    protected $table = 'orders';
}

3. Cambio Dinámico de Conexiones

En algunos casos, necesitarás cambiar la conexión dinámicamente:

<?php

class OrderController extends Controller
{
    public function show($id)
    {
        // Determinar la conexión basada en alguna lógica
        $connection = $this->determineConnection($id);
        
        $order = Order::on($connection)->find($id);
        
        return response()->json($order);
    }
    
    private function determineConnection($id)
    {
        // Ejemplo: IDs antiguos usan la base legacy
        return $id < 1000 ? 'legacy_db' : 'mysql';
    }
}

Casos de Uso Avanzados

1. Separación Read/Write

Laravel permite configurar conexiones separadas para lecturas y escrituras:

<?php

'mysql' => [
    'read' => [
        'host' => [
            'replica1.mysql.com',
            'replica2.mysql.com',
        ],
    ],
    'write' => [
        'host' => 'master.mysql.com',
    ],
    'driver' => 'mysql',
    'database' => 'database',
    'username' => 'root',
    'password' => '',
    'charset' => 'utf8mb4',
    'collation' => 'utf8mb4_unicode_ci',
    'prefix' => '',
],

2. Transacciones con Múltiples Conexiones

Cuando necesitas garantizar la consistencia entre múltiples bases de datos:

<?php

DB::transaction(function () {
    DB::connection('mysql')->table('orders')->insert([/*...*/]);
    
    DB::connection('segunda_db')->transaction(function () {
        DB::table('inventory')->update([/*...*/]);
    });
});

3. Multi-tenant con Base de Datos por Cliente

<?php

class Tenant extends Model
{
    public function configure()
    {
        config([
            'database.connections.tenant' => [
                'driver' => 'mysql',
                'host' => $this->db_host,
                'database' => $this->db_name,
                'username' => $this->db_username,
                'password' => $this->db_password,
            ],
        ]);
        
        DB::purge('tenant');
    }
}

// En un middleware
public function handle($request, Closure $next)
{
    $tenant = Tenant::find($request->tenant_id);
    $tenant->configure();
    
    return $next($request);
}

No te pierdas nuestro curso de Tenancy For Laravel Actualizado

Migraciones con Múltiples Bases de Datos

Para manejar migraciones en diferentes bases de datos:

<?php

// database/migrations/2025_02_04_create_legacy_tables.php
public function up()
{
    Schema::connection('legacy_db')->create('old_users', function (Blueprint $table) {
        $table->id();
        $table->string('name');
        $table->timestamps();
    });
}

Para ejecutar migraciones en una conexión específica:

php artisan migrate --database=legacy_db

Pruebas

Al escribir pruebas, puedes especificar la conexión:

<?php

public function test_can_fetch_legacy_orders()
{
    $order = LegacyOrder::on('legacy_db')->factory()->create();
    
    $response = $this->get("/api/orders/{$order->id}");
    
    $response->assertStatus(200)
        ->assertJson(['id' => $order->id]);
}

Consideraciones y Mejores Prácticas

  1. Monitoreo de Conexiones: Es importante monitorear el número de conexiones activas para evitar sobrecargar los servidores de bases de datos.

  2. Cache de Conexiones: Laravel mantiene un pool de conexiones, pero es importante cerrarlas cuando no se necesiten:

    <?php
    
    DB::connection('segunda_db')->disconnect();
  3. Manejo de Errores: Implementa un manejo robusto de errores para casos donde una base de datos no esté disponible:

    <?php
    
    try {
        DB::connection('legacy_db')->getPdo();
    } catch (\Exception $e) {
        Log::error('No se pudo conectar a la base legacy: ' . $e->getMessage());
        // Implementar lógica de fallback
    }
  4. Logging y Monitoreo: Es recomendable implementar logging personalizado para rastrear el uso de conexiones:

    <?php
    
    DB::beforeExecuting(function ($query, $bindings, $connection) {
        Log::info("Ejecutando consulta en la conexión: " . $connection->getName());
    });

Conclusión

La capacidad de Laravel para manejar múltiples conexiones a bases de datos es una característica poderosa que permite implementar arquitecturas complejas y escalables. Ya sea que estés construyendo una aplicación multi-tenant, integrando sistemas legacy, o implementando estrategias de escalamiento con réplicas de lectura, Laravel proporciona las herramientas necesarias para manejar estos escenarios de manera elegante y eficiente.

Recuerda siempre considerar las implicaciones de performance y mantenibilidad al diseñar sistemas con múltiples bases de datos, y asegúrate de implementar un monitoreo adecuado para detectar y resolver problemas de manera proactiva.

school Curso completo

Curso Laravel 12
Completo 2026

El único curso 100% actualizado que incluye Laravel 12, Livewire 3, Vue 3, React 19 e Inertia 2. Aprende con proyectos reales y las últimas funcionalidades.

access_time 8 horas de contenido
layers 4 tecnologías en 1
update 100% actualizado
code Proyectos prácticos
Ver Curso Laravel 12 arrow_forward

star Incluido en cualquier suscripción

Rutas de aprendizaje