如何在现有的数据库上运行Laravel迁移

251 阅读4分钟

在现有数据库上运行Laravel迁移程序

在这篇文章中,我们将使用Laravel在一个现有的数据库上运行迁移,并有一个样本表,而不需要安装任何包。

想象一下,你的公司需要改变并使用Laravel,从原始的PHP技术或从其他框架转移到Laravel。除此之外, 还有一个现有的数据库, 里面有几千条, 甚至几百万条的记录.

你会先删除数据库,然后运行新的Laravel迁移吗?或者你会创建新的迁移并做一些脆弱的数据导出?你也可以就问题的复杂性向公司提出建议,对吗?

上面讨论的所有选项都不是最合适的选择。我们需要一种方法,在现有的表上谨慎地运行我们的迁移。本文将介绍如何在不干扰任何已有数据的情况下做到这一点。

简要概述

当我们想在Laravel中创建一个数据库表时, 我们首先需要创建这个表的模型.接下来,在模型中,我们设置表的名称和它的字段。然后, 我们使用模型的值来创建表的迁移。

一个迁移文件包含了字段的名称和数据类型。Laravel,默认情况下,为表创建时间戳字段和你提供的字段一起。但如果你不想要时间戳字段呢?你会如何处理这个问题呢?

然后, 我们运行所有的迁移, 我们在我们的环境变量中指定的数据库中创建表。Laravel的官方[文档]只照顾到了新创建的表和数据库。它并没有显示如何处理已经存在的表。

我们将看到如何对现有的表和数据库进行处理。这篇文章是基于Laravel的Eloquent ORM,我已经给出了指向其文档的链接。Eloquent Object Relational Mapper (ORM)给了我们一个更简单的方法来操作我们的数据库,而不需要太在意SQL查询代码。

前提条件

这篇文章有点高级, 所以需要有Laravel的经验。

开始吧

我们将在这些截图中显示的现有数据库上创建一些迁移。它并没有很多记录。它只是为了演示这篇文章。

database screenshot

我们可以看到,它有五个字段。

  1. ID
  2. 子名
  3. 班级名称
  4. 教师代码
  5. 状态

该表被命名为class_subjects,数据库被命名为terrence_time。你可以选择你喜欢的名字。我们继续创建一个简单的Laravel应用程序。在这篇文章中, 让我们把它称为迁移-测试.

    $laravel new migration-test

下一步是创建Laravel模型和迁移。

$php artisan make:model class_subjects -m

-m 标志会创建相应的迁移。否则, 你可以同时做这两件事,如下图所示。

模型

$php artisan make:model class_subjects

迁移

$php artisan make:migration class_subjects

当你检查你的工作目录时, 你会看到迁移和模型文件.

migration screenshot

迁移文件(是最下面的那个)

model screenshot

模型文件 (最上面的那个)

修改模型文件

<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class class_subjects extends Model
{
    use HasFactory;
    protected $table = ‘class_subjects’;
    public $timestamps = false;
    protected $primaryKey = ‘ID’;
    protected $fillable = [‘ID’,‘SUB_NAME’,‘CLASS_NAME’,‘TEACHER_CODE’,‘STATUS’];
}

我们添加表名和表中的字段.$fillable 在Laravel中是用来设置可大量指定的字段的.还有一个$guarded ,用来设置不能被大量分配的字段(受保护的字段)。在这种情况下, 我们希望我们所有的字段都是可修改的.我们将使用$fillable

大规模赋值是使用一个数据结构(如数组)一次性修改多个字段的值。

我们把timestamps变量设置为false ,因为我们没有在我们的表中添加timestamp字段。设置为false ,指示Laravel不要创建默认的时间戳字段。

修改迁移文件

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateClassSubjectsTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        if (!Schema::hasTable(‘class_subjects’)) {
            // Code to create table
            Schema::create(‘class_subjects’, function (Blueprint $table) {
                $table->id();
                $table->integer(‘ID’);
                $table->string(‘SUB_NAME’, 30);
                $table->string(‘CLASS_NAME’, 30);
                $table->integer(‘TEACHER_CODE’);
                $table->string(‘STATUS’, 30);
            });
        }
    }
    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::dropIfExists(‘class_subjects’);
    }
}

在这里, 我们首先检查表是否存在, 按照惯例, 使用这个if 语句:

if (!Schema::hasTable(‘class_subjects’)){
    //code
}

我们这样做是为了让Laravel不会取代我们现有的表。如果它不存在, 那么它就用预定义的字段来创建这个表.你可以把if 语句里面的代码留空,因为我们已经有了这个表。但由于正确的编码道德,我们添加了代码。

运行迁移程序

如果你是在本地主机上工作,你可以使用这个终端命令来运行迁移程序。

$php artisan migrate

如果你是在一个实时服务器上,你将不得不运行一个自动运行迁移的脚本。为了简单起见,我们将把我们的代码放在routes/web 文件中,并通过在浏览器中输入路由来调用它。

Route::get(‘run-migrations’, function () {
    try {
        //the migrate command
        return Artisan::call(‘migrate’);
    } catch (Exception $e) {
        //get the error message and display the error
        $e->getMessage();
        print($e);
    }
});

运行成功后,我们应该在phpMyAdmin中找到迁移的信息。

migration two

打开它,我们应该看到。

migration three

我们还将看到,我们的表没有被篡改。

final table screenshot

就这样了。

总结

简而言之,我们创建了一个Laravel应用程序,添加了模型和迁移,然后运行迁移来适应一个已经创建的表。

这是一篇针对Laravel的文章,但你可以在你使用的技术中使用同样的逻辑。我希望你能得到一些启发。

有一个伟大的编码冒险。