【问题标题】:Laravel - Do Logic in config/database.phpLaravel - 在 config/database.php 中做逻辑
【发布时间】:2019-09-07 08:44:13
【问题描述】:

众所周知,在 Laravel 中 config/database.php 是一堆 arrays 和 values。但是在某些情况下,我需要在那里做一些逻辑,我设法在config/database.php 中做一些简单的逻辑,它可以按我的意愿工作(可以参考下面的代码),但我想知道它是否很好/实用这样做?

如果不实用,您能否建议获得与以下相同结果的其他方法?

'connections' => [

    'mysql' => (function(){ 
        $config = [
            'driver' => 'mysql',
            'host' => env('DB_HOST', '127.0.0.1'),
            'port' => env('DB_PORT', '3306'),
            'database' => env('DB_DATABASE', 'live_db'),
            'username' => env('DB_USERNAME', 'myuser'),
            'password' => env('DB_PASSWORD', '2309423234'),
            'unix_socket' => env('DB_SOCKET', ''),
            'charset' => 'utf8',
            'collation' => 'utf8_unicode_ci',
            'prefix' => 'gn_',
            //'prefix_indexes' => true,
            'strict' => false,
            'engine' => env('DB_ENGINE', null),
        ]; 

        // do some logic here (and it's working!!)
        // but........
        // is it okay to do like this?
        if(env('DB_WITH_SSLMODE', false)){
            $config += [
                'sslmode' => env('DB_SSLMODE', 'prefer'),
                'options'   => [
                    PDO::MYSQL_ATTR_SSL_CA    => env('DB_OPT_MYSQL_ATTR_SSL_CA', 'C:\wamp64\bin\cloudsql\certificates\server-ca.pem'),
                    PDO::MYSQL_ATTR_SSL_CERT    => env('DB_OPT_MYSQL_ATTR_SSL_CERT', 'C:\wamp64\bin\cloudsql\certificates\client-cert.pem'),
                    PDO::MYSQL_ATTR_SSL_KEY    => env('DB_OPT_MYSQL_ATTR_SSL_KEY', 'C:\wamp64\bin\cloudsql\certificates\client-key.pem'),
                    PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('DB_OPT_MYSQL_ATTR_SSL_VERIFY_SERVER_CERT', false)
                ],
            ];
        }

        return $config;
    })(),

],

【问题讨论】:

    标签: database laravel config


    【解决方案1】:

    如何使用三元运算符? (几乎就像在 laravel 5.8 中默认完成的那样)。

    注意:第一个解决方案不会从配置数组中删除 sslmode。如果您需要这样做,请选择第二个选项!

    1) 它应该像这样工作:

    'connections' => [
        'mysql' => [
            'driver' => 'mysql',
            'host' => env('DB_HOST', '127.0.0.1'),
            'port' => env('DB_PORT', '3306'),
            'database' => env('DB_DATABASE', 'forge'),
            'username' => env('DB_USERNAME', 'forge'),
            'password' => env('DB_PASSWORD', ''),
            'unix_socket' => env('DB_SOCKET', ''),
            'charset' => 'utf8mb4',
            'collation' => 'utf8mb4_unicode_ci',
            'prefix' => '',
            'prefix_indexes' => true,
            'strict' => true,
            'engine' => null,
            'sslmode' => env('DB_WITH_SSLMODE') ? env('DB_SSLMODE','prefer') : null,
            'options' => (extension_loaded('pdo_mysql') && env('DB_WITH_SSLMODE')) ? [
                PDO::MYSQL_ATTR_SSL_CA => env('MYSQL_ATTR_SSL_CA'),
                PDO::MYSQL_ATTR_SSL_CERT => env('MYSQL_ATTR_SSL_CERT'),
                PDO::MYSQL_ATTR_SSL_KEY => env('MYSQL_ATTR_SSL_KEY'),
                PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('MYSQL_ATTR_SSL_VERIFY_SERVER_CERT')
            ] : [],
        ],
    ],
    

    或

    2) 肮脏的解决方案但有一个条件:

    'connections' => [
        'mysql' => array_merge([
            'driver' => 'mysql',
            'host' => env('DB_HOST', '127.0.0.1'),
            'port' => env('DB_PORT', '3306'),
            'database' => env('DB_DATABASE', 'forge'),
            'username' => env('DB_USERNAME', 'forge'),
            'password' => env('DB_PASSWORD', ''),
            'unix_socket' => env('DB_SOCKET', ''),
            'charset' => 'utf8mb4',
            'collation' => 'utf8mb4_unicode_ci',
            'prefix' => '',
            'prefix_indexes' => true,
            'strict' => true,
            'engine' => null
        ], (extension_loaded('pdo_mysql') && env('DB_WITH_SSLMODE')) ? [
            'sslmode' => env('DB_SSLMODE', 'prefer'),
            'options' => [
                PDO::MYSQL_ATTR_SSL_CA => env('MYSQL_ATTR_SSL_CA'),
                PDO::MYSQL_ATTR_SSL_CERT => env('MYSQL_ATTR_SSL_CERT'),
                PDO::MYSQL_ATTR_SSL_KEY => env('MYSQL_ATTR_SSL_KEY'),
                PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('MYSQL_ATTR_SSL_VERIFY_SERVER_CERT')
            ]
        ] : [ 'options' => [] ]),
    ],
    

    然后将 env() 中的默认值移动到 .env 文件中(注意我删除了 DB_OPT_ 前缀):

    DB_WITH_SSLMODE=true
    MYSQL_ATTR_SSL_CA=C:\wamp64\bin\cloudsql\certificates\server-ca.pem
    MYSQL_ATTR_SSL_CERT=C:\wamp64\bin\cloudsql\certificates\client-cert.pem
    MYSQL_ATTR_SSL_KEY=C:\wamp64\bin\cloudsql\certificates\client-key.pem
    MYSQL_ATTR_SSL_VERIFY_SERVER_CERT=false
    

    因此,如果您将 DB_WITH_SSLMODE 设置为 false,则会返回一个空数组并且不会启用 ssl。

    注意:我认为您指定的 sslmode 仅适用于 PostgreSQL 连接,这不是您的情况。

    【讨论】:

    • 'sslmode' => env('DB_SSLMODE', 'prefer'),??放在哪里?
    • 阅读答案底部的注释:只有 PostgreSQL 连接才需要它。如果您尝试该配置,它应该可以正常工作
    • 其实我需要它...在我的实时服务器中,如果我删除sslmode,则会显示错误...所以我需要sslmode..
    • 在我的live server 中,我需要打开 SSL……但在我的本地主机中,我需要关闭 SSL……相信我,第一个解决方案不起作用……我已经尝试过...如果我想禁用 SSL,我必须删除sslmode 属性...如果我不删除它并且我只是将其设为空白值(例如'sslmode'=>''),它将引发错误..但是,肮脏的(第二个)解决方案正在工作......感谢分享......我赞成你的回答......
    • 好的,我后来想你需要完全删除解决方案。如果是这种情况,第二个解决方案就是要走的路。
    【解决方案2】:

    您可以为此创建一个服务提供者:

    class SSLServiceProvider extends ServiceProvider
    {
        /**
         * Bootstrap any application services.
         *
         * @return void
         */
        public function boot(Kernel $kernel)
        {
    
        }
    
        /**
         * Register any application services.
         *
         * @return void
         */
        public function register()
        {
            $config = \Config::get('database.connections.mysql');
    
            if (env('DB_WITH_SSLMODE', false)) {
                $config += [
                    'sslmode' => env('DB_SSLMODE', 'prefer'),
                    'options' => [
                        \PDO::MYSQL_ATTR_SSL_CA => env('DB_OPT_MYSQL_ATTR_SSL_CA',
                            'C:\wamp64\bin\cloudsql\certificates\server-ca.pem'),
                        \PDO::MYSQL_ATTR_SSL_CERT => env('DB_OPT_MYSQL_ATTR_SSL_CERT',
                            'C:\wamp64\bin\cloudsql\certificates\client-cert.pem'),
                        \PDO::MYSQL_ATTR_SSL_KEY => env('DB_OPT_MYSQL_ATTR_SSL_KEY',
                            'C:\wamp64\bin\cloudsql\certificates\client-key.pem'),
                        \PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('DB_OPT_MYSQL_ATTR_SSL_VERIFY_SERVER_CERT', false)
                    ],
                ];
            }
    
            \Config::set('database.connections.mysql', $config);
    
        }
    
    }
    

    别忘了在 config/app.php 中注册你的服务提供者

    App\Providers\SSLServiceProvider::class,
    

    【讨论】:

    • 我的新知识...谢谢...我确定它有效,但我仍然觉得这个答案不实用...所以我无法标记您的答案...但我赞成这个答案....感谢分享这个...
    • 不要在配置文件中使用任何 env() 调用,因为如果启用配置缓存 (php artisan optimize/php artisan config:cache),配置文件夹外的任何 env 调用都将返回空值。
    • @mdexp ,,, 是的,这是有道理的...这意味着如果我们使用config:cache...,则此答案不合适...对吗?
    • 对,documentation中也有说明
    【解决方案3】:

    其实你也可以做一些简单的事情:

    $database = [
        'connections' => [
            'mysql' => [
                'driver' => 'mysql',
                'host' => env('DB_HOST', '127.0.0.1'),
                'port' => env('DB_PORT', '3306'),
                'database' => env('DB_DATABASE', 'live_db'),
                'username' => env('DB_USERNAME', 'myuser'),
                'password' => env('DB_PASSWORD', '2309423234'),
                'unix_socket' => env('DB_SOCKET', ''),
                'charset' => 'utf8',
                'collation' => 'utf8_unicode_ci',
                'prefix' => 'gn_',
                //'prefix_indexes' => true,
                'strict' => false,
                'engine' => env('DB_ENGINE', null),
            ]
        ]
    ];
    
    if(env('DB_WITH_SSLMODE', false)){
        $database['connections']['mysql'] += [
            'sslmode' => env('DB_SSLMODE', 'prefer'),
            'options'   => [
                PDO::MYSQL_ATTR_SSL_CA    => env('DB_OPT_MYSQL_ATTR_SSL_CA', 'C:\wamp64\bin\cloudsql\certificates\server-ca.pem'),
                PDO::MYSQL_ATTR_SSL_CERT    => env('DB_OPT_MYSQL_ATTR_SSL_CERT', 'C:\wamp64\bin\cloudsql\certificates\client-cert.pem'),
                PDO::MYSQL_ATTR_SSL_KEY    => env('DB_OPT_MYSQL_ATTR_SSL_KEY', 'C:\wamp64\bin\cloudsql\certificates\client-key.pem'),
                PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('DB_OPT_MYSQL_ATTR_SSL_VERIFY_SERVER_CERT', false)
            ]
        ];
    }
    
    return $database;
    
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-09-05
      • 2023-03-29
      • 2013-10-20
      • 2016-05-06
      • 2018-08-30
      • 2021-10-09
      • 2016-07-08
      相关资源
      最近更新 更多