在哪里为PHP应用程序存储数据库登录凭证

时间:2021-05-29 05:01:22

We have a development server and a live server with different database connection details (username, password, etc).

我们有一个开发服务器和一个具有不同数据库连接细节(用户名、密码等)的活动服务器。

Currently we're storing BOTH the database connection details in a initial.php and one is selected if a DEFINE statement is present. We manually add that DEFINE statement on our live server.

目前,我们将数据库连接的详细信息存储在初始状态中。如果存在定义语句,则选择php和其中一个。我们在活动服务器上手动添加定义语句。

Is this a safe approach? What are better / alternative approachs for managing DB connection security?

这种方法安全吗?对于管理DB连接安全性,什么是更好的/替代的方法?

One consequence of this is that every developer can see the database connection details and that's a bit risky...

这样做的一个后果是,每个开发人员都可以看到数据库连接细节,这有点冒险……

5 个解决方案

#1


12  

I use an .ini-file, which is then parsed via parse_ini_file(INI_FILENAME_HERE, true). This file isn't under version control (as are the php-/template-/whatever-files). So on every machine I create that file (.database.ini) for the respective database connection.

我使用一个.ini文件,然后通过parse_ini_file(INI_FILENAME_HERE, true)解析它。这个文件不在版本控制之下(php-/template-/whatever-files也是如此)。因此,在每台机器上,我都为各自的数据库连接创建这个文件(.database.ini)。

Example .ini-file for a MySQL-connection, using PDO:

示例.ini文件用于mysql连接,使用PDO:

[db_general]
driver = "mysql"
user = "USERNAME"
password = "PASSWORD"

; DSN
; see http://www.php.net/manual/en/pdo.drivers.php
[db_data_source_name]
host = "localhost"
port = 3306
dbname = "DATABASE_NAME"

; specify PDO-options, provide keys without PDO::
; see http://www.php.net/manual/en/pdo.drivers.php
[db_pdo_options]
MYSQL_ATTR_INIT_COMMAND = "SET NAMES utf8"

; specify more PDO-attributes, provide keys without PDO::
; see http://php.net/manual/en/pdo.setattribute.php
[db_pdo_attributes]
ATTR_CASE = "PDO::CASE_LOWER"
ATTR_ERRMODE = "PDO::ERRMODE_EXCEPTION"
ATTR_EMULATE_PREPARES = false

Since one can't use :: within .ini-file-keys, use constant('PDO::' . $iniKey) in your code to get the desired PDO-constants.

由于不能在.ini-file-keys中使用::,所以要使用常量('PDO::')。$iniKey)在您的代码中获取所需的pdo常量。

#2


2  

I recently had to deal with this issue, and what I did was create two new database users. The first had no privileges at all, other than read privileges on tables in his own schema. The second had insert privileges to a "load" table I would be populating with my code.

我最近不得不处理这个问题,我所做的就是创建两个新的数据库用户。第一个完全没有特权,除了在自己的模式中读取表上的特权。第二个具有对我将用代码填充的“load”表的插入特权。

The unprivileged user got a "credentials" table in his schema, which held the credentials and password of the insert user (along with some other parameters I needed for my app). So the code only contained the credentials for the unprivileged user, hard-coded and changed periodically, and at runtime it would look up the credentials it needed to do inserts. The lookup took place behind our firewall, between servers, so it wasn't something an outsider could eavesdrop on.

无特权的用户在他的模式中有一个“凭据”表,其中包含插入用户的凭据和密码(以及我的应用需要的其他一些参数)。因此,代码只包含无特权用户的凭据(硬编码和定期更改),在运行时它将查找进行插入所需的凭据。查找发生在我们的防火墙后面,服务器之间,所以它不是外人可以偷听的东西。

It wasn't developers I was worried about, it was outsiders and power users, who could theoretically gain access to the web server and peek at ini files. This way, only developers and DBAs could snoop (and we all know each other). Anyone else would have to figure out how to query the database, figure out what SQL to use, figure out how to run code... Not impossible, but certainly a gigantic multi-step pain in the butt and not worth it.

我担心的不是开发人员,而是外来者和权力用户,他们理论上可以访问web服务器并查看ini文件。这样,只有开发人员和dba才能窥探(我们彼此都知道)。任何人都必须弄清楚如何查询数据库,如何使用SQL,如何运行代码……不是不可能的,但肯定是一个巨大的多步疼痛在臀部而且不值得。

Pretty safe -- in theory, anyway...

相当安全——无论如何,在理论上……

#3


1  

Another approach would be to setup environment variables on the live and development machine and access them from the code... I don't know much php, but in python that would be:

另一种方法是在活动和开发机器上设置环境变量,并从代码中访问它们……我不太懂php,但在python中,它是:

import os
password = os.environ('DB_PASS')

This lets you distribute accounts and passwords as needed to developers and deployed servers. Depending on their permissions on that machine, developers could be prevented from having any access to the live password.

这使您可以根据需要将帐户和密码分发给开发人员和部署的服务器。根据他们在这台机器上的权限,可以阻止开发人员访问实时密码。

#4


0  

Is kinda difficult to protect your application against the developers that are using it. My suggestions will be to load all passwords from a config file and create 2 separate environments: one for developing and one for the production server. Give full access to developers to the developing machine and when moving to the production server the application will feed itself with the production config which will be stored only on that machine and thus inaccessible to most developers. This type of security is more of a process and you have to define several steps, like who has access to the production machines and who is doing the publishing... etc.

要保护应用程序免受使用它的开发人员的攻击有点困难。我的建议是从配置文件加载所有密码,并创建两个独立的环境:一个用于开发,一个用于生产服务器。为开发人员提供开发机器的完全访问权限,当迁移到生产服务器时,应用程序将为自己提*品配置,这些配置将仅存储在该机器上,因此大多数开发人员无法访问。这种类型的安全性更多的是一个过程,您必须定义几个步骤,比如谁可以访问生产机器,谁正在发布……等。

#5


0  

Is this a safe approach?

这种方法安全吗?

It depends on your definition of safe.

这取决于你对安全的定义。

every developer can see the database connection details

每个开发人员都可以看到数据库连接的详细信息

AFAIK, other than using the default username/password/database in the php.ini file, that problem is pretty much unavoidable (and using the defaults mean they've automatically got access to the database anyway).

AFAIK,除了在php中使用默认的用户名/密码/数据库。ini文件,这个问题是不可避免的(使用默认值意味着他们已经自动地访问数据库)。

I guess you could use different include files encrypted using zend encoder with a function which returns database handles - and set up the scope and permissions for different files, but its tricky to isolate the PHP code the underlying data. Another approach would be to restrict everything to webservices and implement an extended permissions model in the webservice tier.

我猜您可以使用zend encoder加密的不同的include文件,该文件带有一个函数,该函数返回数据库句柄——并为不同的文件设置范围和权限,但是要将PHP代码与底层数据隔离是很困难的。另一种方法是将所有内容都限制在webservices中,并在webservice层中实现扩展的权限模型。

#1


12  

I use an .ini-file, which is then parsed via parse_ini_file(INI_FILENAME_HERE, true). This file isn't under version control (as are the php-/template-/whatever-files). So on every machine I create that file (.database.ini) for the respective database connection.

我使用一个.ini文件,然后通过parse_ini_file(INI_FILENAME_HERE, true)解析它。这个文件不在版本控制之下(php-/template-/whatever-files也是如此)。因此,在每台机器上,我都为各自的数据库连接创建这个文件(.database.ini)。

Example .ini-file for a MySQL-connection, using PDO:

示例.ini文件用于mysql连接,使用PDO:

[db_general]
driver = "mysql"
user = "USERNAME"
password = "PASSWORD"

; DSN
; see http://www.php.net/manual/en/pdo.drivers.php
[db_data_source_name]
host = "localhost"
port = 3306
dbname = "DATABASE_NAME"

; specify PDO-options, provide keys without PDO::
; see http://www.php.net/manual/en/pdo.drivers.php
[db_pdo_options]
MYSQL_ATTR_INIT_COMMAND = "SET NAMES utf8"

; specify more PDO-attributes, provide keys without PDO::
; see http://php.net/manual/en/pdo.setattribute.php
[db_pdo_attributes]
ATTR_CASE = "PDO::CASE_LOWER"
ATTR_ERRMODE = "PDO::ERRMODE_EXCEPTION"
ATTR_EMULATE_PREPARES = false

Since one can't use :: within .ini-file-keys, use constant('PDO::' . $iniKey) in your code to get the desired PDO-constants.

由于不能在.ini-file-keys中使用::,所以要使用常量('PDO::')。$iniKey)在您的代码中获取所需的pdo常量。

#2


2  

I recently had to deal with this issue, and what I did was create two new database users. The first had no privileges at all, other than read privileges on tables in his own schema. The second had insert privileges to a "load" table I would be populating with my code.

我最近不得不处理这个问题,我所做的就是创建两个新的数据库用户。第一个完全没有特权,除了在自己的模式中读取表上的特权。第二个具有对我将用代码填充的“load”表的插入特权。

The unprivileged user got a "credentials" table in his schema, which held the credentials and password of the insert user (along with some other parameters I needed for my app). So the code only contained the credentials for the unprivileged user, hard-coded and changed periodically, and at runtime it would look up the credentials it needed to do inserts. The lookup took place behind our firewall, between servers, so it wasn't something an outsider could eavesdrop on.

无特权的用户在他的模式中有一个“凭据”表,其中包含插入用户的凭据和密码(以及我的应用需要的其他一些参数)。因此,代码只包含无特权用户的凭据(硬编码和定期更改),在运行时它将查找进行插入所需的凭据。查找发生在我们的防火墙后面,服务器之间,所以它不是外人可以偷听的东西。

It wasn't developers I was worried about, it was outsiders and power users, who could theoretically gain access to the web server and peek at ini files. This way, only developers and DBAs could snoop (and we all know each other). Anyone else would have to figure out how to query the database, figure out what SQL to use, figure out how to run code... Not impossible, but certainly a gigantic multi-step pain in the butt and not worth it.

我担心的不是开发人员,而是外来者和权力用户,他们理论上可以访问web服务器并查看ini文件。这样,只有开发人员和dba才能窥探(我们彼此都知道)。任何人都必须弄清楚如何查询数据库,如何使用SQL,如何运行代码……不是不可能的,但肯定是一个巨大的多步疼痛在臀部而且不值得。

Pretty safe -- in theory, anyway...

相当安全——无论如何,在理论上……

#3


1  

Another approach would be to setup environment variables on the live and development machine and access them from the code... I don't know much php, but in python that would be:

另一种方法是在活动和开发机器上设置环境变量,并从代码中访问它们……我不太懂php,但在python中,它是:

import os
password = os.environ('DB_PASS')

This lets you distribute accounts and passwords as needed to developers and deployed servers. Depending on their permissions on that machine, developers could be prevented from having any access to the live password.

这使您可以根据需要将帐户和密码分发给开发人员和部署的服务器。根据他们在这台机器上的权限,可以阻止开发人员访问实时密码。

#4


0  

Is kinda difficult to protect your application against the developers that are using it. My suggestions will be to load all passwords from a config file and create 2 separate environments: one for developing and one for the production server. Give full access to developers to the developing machine and when moving to the production server the application will feed itself with the production config which will be stored only on that machine and thus inaccessible to most developers. This type of security is more of a process and you have to define several steps, like who has access to the production machines and who is doing the publishing... etc.

要保护应用程序免受使用它的开发人员的攻击有点困难。我的建议是从配置文件加载所有密码,并创建两个独立的环境:一个用于开发,一个用于生产服务器。为开发人员提供开发机器的完全访问权限,当迁移到生产服务器时,应用程序将为自己提*品配置,这些配置将仅存储在该机器上,因此大多数开发人员无法访问。这种类型的安全性更多的是一个过程,您必须定义几个步骤,比如谁可以访问生产机器,谁正在发布……等。

#5


0  

Is this a safe approach?

这种方法安全吗?

It depends on your definition of safe.

这取决于你对安全的定义。

every developer can see the database connection details

每个开发人员都可以看到数据库连接的详细信息

AFAIK, other than using the default username/password/database in the php.ini file, that problem is pretty much unavoidable (and using the defaults mean they've automatically got access to the database anyway).

AFAIK,除了在php中使用默认的用户名/密码/数据库。ini文件,这个问题是不可避免的(使用默认值意味着他们已经自动地访问数据库)。

I guess you could use different include files encrypted using zend encoder with a function which returns database handles - and set up the scope and permissions for different files, but its tricky to isolate the PHP code the underlying data. Another approach would be to restrict everything to webservices and implement an extended permissions model in the webservice tier.

我猜您可以使用zend encoder加密的不同的include文件,该文件带有一个函数,该函数返回数据库句柄——并为不同的文件设置范围和权限,但是要将PHP代码与底层数据隔离是很困难的。另一种方法是将所有内容都限制在webservices中,并在webservice层中实现扩展的权限模型。