根据服务器环境参数来区分
【转】https://blog.youkuaiyun.com/default7/article/details/49329585
Apache 指令中加入
SetEnv RUN_ENV dev
Nginx 中
fastcgi_param RUN_ENV 'dev'
然后重启 Apache/Nginx,我们用 php $_SERVER 来查看是否有 $_SERVER['RUN_ENV'];
在代码中可以这么使用
// 定义运行环境
define('RUN_ENV', isset($_SERVER['RUN_ENV']) ? $_SERVER['RUN_ENV'] : 'production');
require_once DIR_ROOT . '/system/config/' . RUN_ENV . '/config.php';
利用 php.ini 参数设置来区分
我们可以在 php.ini 中直接设置参数,比如我设置了一个参数名为 pro.env 的参数,值为 pro
[Environment]
pro.env=pro
代码中可以这么使用
// 用于cli模式下的判断
$env = ($tmpEnv = get_cfg_var('pro.env')) ? $tmpEnv : 'ceshi';
if (isset($env)) {
define('WEB_ENV', $env);
return require __DIR__ . DIRECTORY_SEPARATOR . 'Config' . DIRECTORY_SEPARATOR . WEB_ENV . '.env.php';
}
利用 php-fpm.conf 设置参数
env[RUNTIME_ENVIROMENT] = test
Caution 由于这些设定是以 FastCGI 标头传递给 php-fpm,php-fpm 不应绑定到外部网可以访问的地址上,否则任何人都能修改 PHP 的配置选项了。参见 listen.allowed_clients。
使用 http 或者 https 来区分
如果访问是通过 https 协议过来的请求,那 $_SERVER 中应该是有 $_SERVER['HTTPS'],对于 HTTPS的判断可以使用下面的方法。
function getIsSecureConnection ()
{
return ((isset($_SERVER['HTTPS']) && strcasecmp($_SERVER['HTTPS'], 'on') === 0) || (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 1)
|| (isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && strcasecmp($_SERVER['HTTP_X_FORWARDED_PROTO'], 'https') === 0));
}
那有的同学就会说了,我打印 $_SERVER 并没有看到有 HTTPS这个参数啊,那没有的话你就需要去设置下你的 Apache 或者 Nginx,这里我仅仅是测试了 Nginx,可以这么设置。参数部分的解释并不那么准确仅做参考,具体可查看 Nginx 官方文档。
location / {
proxy_set_header X-Forwarded-Proto https; # 真实来源协议
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; # 真实来源IP地址
proxy_set_header Host $http_host; # 真实访问域名信息
proxy_redirect off; # 禁止重定向
proxy_pass http://www.baidu.com:80; # 代理转发
}
然后重启 Nginx 后, 查看$_SERVER['HTTPS']是否存在了。
通过区分这个 http 和 https 我们可以在队列方面生产数据的时候加以区分,那消费者也可以通过这个 http 或者 https来区分将数据消费到对应的哪个数据库,因为消费者并不知道要将数据消费到哪里,所以需要你指定。
因为这里我仅仅测试了用 http 和 https这种方法来区分。那上面两种的效果类似,可自行测试。
假如我们要生产数据。我们把正式数据放到键为 https 的数组中,把 测试数据放到 http 的数组中。
// Publisher
$msgbody = [];
if (self::getIsSecureConnection()) {
$msgbody['https'] = $mqbody;
} else {
$msgbody['http'] = $mqbody;
}
$msgbody = json_encode($msgbody);
……
$psrContext->createMessage($msgbody);
// Consumer
while (true) {
if ($message = $consumer->receive()) {
if (self::getIsSecureData($message->getBody())) {
$https_data = self::formatIsSecureData($message->getBody());
} else {
$http_data = self::formatIsSecureData($message->getBody());
}
$consumer->acknowledge($message);
}
}
public static function getIsSecureData ($input = "") // json
{
// check is secure data is http or https
$input = json_decode($input, true);
if (isset($input['http']) && !empty($input['http'])) {
return false; // http
} else if (isset($input['https']) && !empty($input['https'])) {
return true; // https
}
}
public static function formatIsSecureData ($input = "") // json
{
// format is secure data to http or https
$input = json_decode($input, true);
if (isset($input['http']) && !empty($input['http'])) {
return $input['http']; // http
} else if (isset($input['https']) && !empty($input['https'])) {
return $input['https']; // https
}
}
请注意一些其他的问题,那就是通过 URI 模式访问资源和通过 PHP CLI 模式访问资源,服务器参数是有好多不同的
URI 模式有 $_SERVER 中的N多参数, PHP CLI 模式并没有相关参数,如果你的项目中既用到了 URI 模式访问资源也用到了 PHP CLI 模式来执行一些操作,那你区分这块就要下点功夫来调整细节问题。
判断是否为 CLI 模式
function is_cli ()
{
return preg_match("/cli/i", php_sapi_name()) ? true : false;
}
那上面也说过2种设置参数的方法了,cli模式 中并不会有 $_SERVER 参数,所以选择一种加参数的方式就显得格外重要了,可以加在 php.ini 或者 php-fpm.conf 中,通过 get_cfg_var()来获取你的设置并加载相关配置文件。
本文介绍了如何通过Apache、Nginx、PHP等环境变量配置来区分不同运行环境,并提供了使用PHP判断当前环境的方法,包括HTTP与HTTPS的区别。
1090

被折叠的 条评论
为什么被折叠?



