如何通过一个 laravel 安装来处理子域
How can I handle subdomains with one laravel installation
我正在创建一个 laravel 项目,我需要 一个 laravel 安装 并在 的子域中使用它的实例单独的数据库。那些单独的数据库的信息不会在 config/database.php 中。它将从主数据库获取,然后重新连接到另一个数据库。
我没有找到合适的方法。
你有什么想法吗?
感谢您的宝贵时间。
Laravel 支持多个数据库连接。首先,定义 config/database.php
:
中的连接
<?php
return array(
'default' => 'default_connection',
'connections' => array(
// domain.com
'default_connection' => array(
'driver' => 'mysql',
'host' => 'localhost',
'database' => 'primary_database',
'username' => 'username',
'password' => 'password'
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
),
// sub.domain.com
'subdomain_connection' => array(
'driver' => 'mysql',
'host' => 'localhost',
'database' => 'secondary_database',
'username' => 'username',
'password' => 'password'
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
),
),
);
现在要指定您的模型应该使用哪个连接,您可以在模型中设置 $connection
属性:
<?php
class YourModel extends Eloquent {
protected $connection = 'subdomain_connection';
}
您可以通过编程方式设置 $connection
的值。
我会这样做:
为每个域创建一个数据库
在 laravel config/database.php
中设置可用的数据库连接 :
'connections' => [
'mysql_domain_1' => [
'driver' => 'mysql',
/* other config values... */
],
'mysql_domain_2' => [
'driver' => 'mysql',
/* other config values... */
]
];
在请求周期的早期阶段(例如在中间件中),从请求中获取子域,并相应地设置当前数据库连接
例如创建一个中间件并在handle
方法中:
public function handle($request, Closure $next)
{
//check the request URL and get subdomain
//get the db connection associated to the subdomain
//set the connection for this request
Config::set('database.default', $dbConnection);
}
Config::set('database.default', $dbConnection );
将设置整个应用程序在当前请求周期使用的数据库连接
如果你想从数据库中处理这个,那么检查来自http url 的主机名,并根据主机名从main table 调用数据库连接。例如(http://abc.maindomain.com,从 url 获取 abc)
多租户是一种需要小心建模的棘手架构。有几种方法可以实现这种架构。有些人决定使用单个数据库,而其他人则更喜欢使用多个数据库(在您的情况下)。
它们各有优缺点,您需要考虑。在开始对应用程序建模之前,需要考虑很多因素。例如子域的虚拟主机配置、数据库迁移(在需要时回滚所有数据库等)。我将推荐这两个包,它们可以帮助您前进,并让您更深入地了解如何为您的应用程序建模以满足您的需求。
您可以通过以下方式设置数据库配置:
$tenant = Tenant::whereSubDomain($subdomain)->first();
Config::set('database.connections.mysql.database', $tenant->db_name);
Config::set('database.connections.mysql.username',$tenant->db_username);
Config::set('database.connections.mysql.password',$tenant->db_password);
dd(\DB::connection('mysql'));
请参阅此 link Set up dynamic database connection on Multi tenant application 以供参考。
以下是我的处理方法:
在你的config/database.php:
<?php
function getDatabaseConnectionParameters() {
$connectionParams = array();
// add the default connection
// this is your master database
$connParams = array(
'driver' => 'mysql',
'host' => 'localhost',
'database' => 'master',
'username' => 'master_user',
'password' => 'master_password',
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
'strict' => false,
);
array_push($connectionParams, array('mysql' => $connParams);
// TODO: connect to your master database using PDO/mysqli or anything else you know.
// The point is: you can't use Laravel ORM just yet because you are currently setting up its configuration!
// Get the list of subdomain connection parameters and array_push it to $connectionParams just like above.
// Example:
// array_push($connectionParams, array('subdomain' => $subdomainConnParams)
return $connectionParams;
}
return array (
'default' => 'mysql'
,'connections' => getDatabaseConnectionParameters()
)
?>
有了这个,子域特定模型只需要正确指定 $connection。
示例:
<?php
class YourModel extends Eloquent {
protected $connection = 'subdomain';
}
?>
这样,您的子域数据库配置可以保存在您的主数据库中,同时使您的模型简单且 Laravel-ful。
此外,没有使升级 Laravel 版本变得困难的讨厌的黑客攻击。
刚刚偶然发现这个问题,恕我直言,有时最简单的建议是最简单的。
我只是在 /config/database.php 文件的开头放置了一个简单的开关:
switch($_SERVER['HTTP_HOST'])
{
case 'dev.yoursite.com':
$selectedDatabase = 'mysite_dev';
break;
case 'yoursite.com':
default:
$selectedDatabase = 'mysite_live';
break;
}
然后只需使用返回的配置变量中的变量。
return [
'connections' =>
['mysql' =>
['database' => $selectedDatabase,
'username' => 'user_name',
'password' => 'xxxxxxxxx',
],
]
];
我知道这不是 laravel 方法,但如果您只想使用相同的 PHP 编码打开一个快速测试环境,它会让您摆脱困境,但是您的数据库的测试实例。
我正在创建一个 laravel 项目,我需要 一个 laravel 安装 并在 的子域中使用它的实例单独的数据库。那些单独的数据库的信息不会在 config/database.php 中。它将从主数据库获取,然后重新连接到另一个数据库。
我没有找到合适的方法。
你有什么想法吗?
感谢您的宝贵时间。
Laravel 支持多个数据库连接。首先,定义 config/database.php
:
<?php
return array(
'default' => 'default_connection',
'connections' => array(
// domain.com
'default_connection' => array(
'driver' => 'mysql',
'host' => 'localhost',
'database' => 'primary_database',
'username' => 'username',
'password' => 'password'
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
),
// sub.domain.com
'subdomain_connection' => array(
'driver' => 'mysql',
'host' => 'localhost',
'database' => 'secondary_database',
'username' => 'username',
'password' => 'password'
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
),
),
);
现在要指定您的模型应该使用哪个连接,您可以在模型中设置 $connection
属性:
<?php
class YourModel extends Eloquent {
protected $connection = 'subdomain_connection';
}
您可以通过编程方式设置 $connection
的值。
我会这样做:
为每个域创建一个数据库
在 laravel
config/database.php
中设置可用的数据库连接 :
'connections' => [
'mysql_domain_1' => [
'driver' => 'mysql',
/* other config values... */
],
'mysql_domain_2' => [
'driver' => 'mysql',
/* other config values... */
]
];
在请求周期的早期阶段(例如在中间件中),从请求中获取子域,并相应地设置当前数据库连接
例如创建一个中间件并在
handle
方法中:
public function handle($request, Closure $next)
{
//check the request URL and get subdomain
//get the db connection associated to the subdomain
//set the connection for this request
Config::set('database.default', $dbConnection);
}
Config::set('database.default', $dbConnection );
将设置整个应用程序在当前请求周期使用的数据库连接
如果你想从数据库中处理这个,那么检查来自http url 的主机名,并根据主机名从main table 调用数据库连接。例如(http://abc.maindomain.com,从 url 获取 abc)
多租户是一种需要小心建模的棘手架构。有几种方法可以实现这种架构。有些人决定使用单个数据库,而其他人则更喜欢使用多个数据库(在您的情况下)。
它们各有优缺点,您需要考虑。在开始对应用程序建模之前,需要考虑很多因素。例如子域的虚拟主机配置、数据库迁移(在需要时回滚所有数据库等)。我将推荐这两个包,它们可以帮助您前进,并让您更深入地了解如何为您的应用程序建模以满足您的需求。
您可以通过以下方式设置数据库配置:
$tenant = Tenant::whereSubDomain($subdomain)->first();
Config::set('database.connections.mysql.database', $tenant->db_name);
Config::set('database.connections.mysql.username',$tenant->db_username);
Config::set('database.connections.mysql.password',$tenant->db_password);
dd(\DB::connection('mysql'));
请参阅此 link Set up dynamic database connection on Multi tenant application 以供参考。
以下是我的处理方法:
在你的config/database.php:
<?php
function getDatabaseConnectionParameters() {
$connectionParams = array();
// add the default connection
// this is your master database
$connParams = array(
'driver' => 'mysql',
'host' => 'localhost',
'database' => 'master',
'username' => 'master_user',
'password' => 'master_password',
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
'strict' => false,
);
array_push($connectionParams, array('mysql' => $connParams);
// TODO: connect to your master database using PDO/mysqli or anything else you know.
// The point is: you can't use Laravel ORM just yet because you are currently setting up its configuration!
// Get the list of subdomain connection parameters and array_push it to $connectionParams just like above.
// Example:
// array_push($connectionParams, array('subdomain' => $subdomainConnParams)
return $connectionParams;
}
return array (
'default' => 'mysql'
,'connections' => getDatabaseConnectionParameters()
)
?>
有了这个,子域特定模型只需要正确指定 $connection。 示例:
<?php
class YourModel extends Eloquent {
protected $connection = 'subdomain';
}
?>
这样,您的子域数据库配置可以保存在您的主数据库中,同时使您的模型简单且 Laravel-ful。 此外,没有使升级 Laravel 版本变得困难的讨厌的黑客攻击。
刚刚偶然发现这个问题,恕我直言,有时最简单的建议是最简单的。
我只是在 /config/database.php 文件的开头放置了一个简单的开关:
switch($_SERVER['HTTP_HOST'])
{
case 'dev.yoursite.com':
$selectedDatabase = 'mysite_dev';
break;
case 'yoursite.com':
default:
$selectedDatabase = 'mysite_live';
break;
}
然后只需使用返回的配置变量中的变量。
return [
'connections' =>
['mysql' =>
['database' => $selectedDatabase,
'username' => 'user_name',
'password' => 'xxxxxxxxx',
],
]
];
我知道这不是 laravel 方法,但如果您只想使用相同的 PHP 编码打开一个快速测试环境,它会让您摆脱困境,但是您的数据库的测试实例。