如何在AWS Elastic Beanstalk上执行Laravel Artisan迁移


How do I perform Laravel Artisan migrations on AWS Elastic Beanstalk?

我安装了Laravel,并设置了三个具有相应配置目录的环境:

  • 本地
  • 分段
  • 生产

我使用这里描述的php artisan migrate:make create_users_table等创建数据库迁移。

在我的本地环境中,我使用Vagrant和一个简单的MySQL服务器设置;生产我使用AWS RDS。

要为暂存环境配置数据库访问,我有一个app/config/staging/database.php文件,其设置如下:

...
"mysql" => array(
    "driver" => "mysql",
    "host" => $_SERVER["RDS_HOSTNAME"],
    "database" => $_SERVER["RDS_DB_NAME"],
    "username" => $_SERVER["RDS_USERNAME"],
    "password" => $_SERVER["RDS_PASSWORD"],
    "charset" => "utf8",
    "collaction" => "utf8_unicode_ci",
    "prefix" => "",
),
...

我使用git来部署带有git aws.push的应用程序,如下所述。

问题是:部署时,如何在我的暂存(以及以后的生产)EBS服务器上运行迁移?

我通过在项目根目录中创建一个名为.ebextensions的新目录来解决这个问题。在那个目录中,我创建了一个脚本文件my-scripts.config:

.ebextensions/
    my-scripts.config
app/
artisan
bootstrap
...

文件my-scripts.config在EBS部署时执行,是一个YAML文件,如下所示:

container_commands:
    01-migration:
        command: "php /var/app/ondeck/artisan --env=staging migrate"
        leader_only: true

将目录和文件添加到git,提交并运行git aws.push,它就会迁移。

关于.ebextensions中的内容如何工作的解释可以在这里找到。

路径/var/app/ondeck是脚本运行时应用程序所在的位置,之后它将被复制到/var/app/current中。

artisan选项--env=staging有助于告诉artisan它应该在什么环境中运行,这样它就可以从app/config/staging/database.php 中找到正确的数据库设置

如果您需要一种快速而肮脏的方法来记录migrate命令失败的原因,您可能需要尝试"php /var/app/ondeck/artisan --env=staging migrate > /tmp/artisan-migrate.log"之类的方法,以便登录到ec2实例并检查日志。

在oskarth回答之后,在过去几年中,关于AWS Elastic Beanstalk如何部署新应用程序版本的一些说明可能已经更改。根据与.eextensions的container_commands相关的AWS文档;cwd";选项,则工作目录是解压缩的应用程序的暂存目录。这意味着在部署过程中,实例下的用户将位于/var/app/stating/,即提取的应用程序源版本所在的位置。因此,artisan命令可以单独执行,也可以按照var/app/staging/路径执行,而不是像下面这样执行:

container_commands:
01-migration:
    command: "php artisan --env=staging migrate"
    leader_only: true

或者这个

container_commands:
01-migration:
    command: "php /var/app/staging/artisan --env=staging migrate"
    leader_only: true

我已经使用上面的两种配置部署了我的项目。经过数小时查看eb engine.log文件并反复阅读文档后,我发现了这一点。我希望任何人在阅读后也能花这么长时间。可以通过在终端上、环境控制台上或通过与环境相关的S3存储桶执行eb logs命令来访问日志。文档中几乎解释了所有内容。我没有对奥斯卡的回答发表评论,我还没有被允许!

ps。/var/app/staging路径与laravel中的staging环境无关。

这里值得一提的是,如果人们在Beanstalk上使用dockerised容器来运行他们的应用程序,则必须在容器内运行。

files:
    "/opt/elasticbeanstalk/hooks/appdeploy/post/98_build_app.sh":
        mode: "000755"
        owner: root
        group: root
        content: |
            #!/usr/bin/env bash
            echo "Running laravel migrations" >> /var/log/eb-activity.log
            docker exec $(docker ps -qf name=php-fpm) sh -c "php artisan --env=staging migrate --force || echo Migrations didnt run" >> /var/log/eb-activity.log 2>&1

问题是容器名称每次都会更改。

因此,docker ps -qf name=php-fpm部分只需要获得一个容器名称包含php-fpm的容器。因此,用与您想要在哪个容器上运行它相匹配的其他东西来替换它

还要使用--force,因为否则,它将尝试并等待提示