如何避免存储凭据以使用 JDBC 连接到 Oracle?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/126720/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-18 17:16:29  来源:igfitidea点击:

How to avoid storing credentials to connect to Oracle with JDBC?

oraclejdbccredentials

提问by Hans Doggen

Is it possible to setup a JDBC connection to Oracle without providing username/password information in a configuration file (or in any other standard readable location)?

是否可以在配置文件(或任何其他标准可读位置)中不提供用户名/密码信息的情况下设置到 Oracle 的 JDBC 连接?

Typically applications have a configuration file that contains setup parameters to connect to a database. Some DBAs have problems with the fact that usernames and passwords are in clear text in config files.

通常,应用程序有一个配置文件,其中包含连接到数据库的设置参数。一些 DBA 对用户名和密码在配置文件中采用明文这一事实存在问题。

I don't think this is possible with Oracle and JDBC, but I need some confirmation...

我认为 Oracle 和 JDBC 不可能做到这一点,但我需要一些确认...

A possible compromise is to encrypt the password in the config file and decrypt it before setting up the connection. Of course, the decryption key should not be in the same config file. This will only solve accidental opening of the config file by unauthorized users.

一个可能的折衷方案是加密配置文件中的密码并在设置连接之前对其进行解密。当然,解密密钥不应该在同一个配置文件中。这只会解决未经授权的用户意外打开配置文件的问题。

回答by stili

You may want to try Kerberos which can use the OS user's credentials and adding the OS user to the database as identified externally. Make sure that you use Kerberos and not the old way of doing this, which had serious security issues.

您可能想尝试 Kerberos,它可以使用操作系统用户的凭据并将操作系统用户添加到外部识别的数据库中。确保您使用 Kerberos 而不是执行此操作的旧方法,它具有严重的安全问题。

For Kerberos support you would need the advanced security option and a recent JDBC driver, probably 11g version. Before trying to get it to work in Java, try it out in Sql*Plus using '/' as username and empty password. "select user from dual" should give you user@domain. You may also find that there is a fundamental difference between using thin or OCI driver when it comes to Kerberos configuration.

对于 Kerberos 支持,您需要高级安全选项和最新的 JDBC 驱动程序,可能是 11g 版本。在尝试让它在 Java 中工作之前,先在 Sql*Plus 中尝试使用“/”作为用户名和空密码。“从双重选择用户”应该给你 user@domain。您可能还会发现,在 Kerberos 配置方面,使用瘦驱动程序或 OCI 驱动程序之间存在根本区别。

回答by David G

You definitely don't want to be able to connect to the database without credentials because that makes the database vulnerable.

您绝对不希望能够在没有凭据的情况下连接到数据库,因为这会使数据库容易受到攻击。

This is a general problem, how do I store credentials needed to access external systems? WebLogic has a credential mapper to solve this problem, in which credentials (encrypted) are stored in embedded LDAP. Many Oracle products use a credential store facility that stores credentials in Oracle wallet.

这是一个普遍问题,如何存储访问外部系统所需的凭据?WebLogic 有一个凭证映射器来解决这个问题,其中凭证(加密)存储在嵌入式 LDAP 中。许多 Oracle 产品使用凭证存储工具将凭证存储在 Oracle 钱包中。

In the question, you provided the answer. Store the password encrypted and decrypt when you need it. Obviously you have to use symmetric encryption algorithm such as 3DES so you can decrypt it. Make sure the symmetric key is not something that can be guessed.

在问题中,您提供了答案。存储密码加密并在需要时解密。显然,您必须使用对称加密算法(例如 3DES)才能对其进行解密。确保对称密钥不是可以猜到的东西。

The trick is where you keep the symmetric key needed for en/de-cryption. You can put it in a file that is secured through the OS or you can keep it in the code, but then you need to keep the code secure. You can also generate the key if you use a technique that will produce the same key and the algorithm is reasonably secure.

诀窍在于您保留加密/解密所需的对称密钥。您可以将其放在通过操作系统保护的文件中,也可以将其保存在代码中,但随后您需要确保代码安全。如果您使用的技术可以生成相同的密钥并且算法相当安全,您也可以生成密钥。

If you can keep the code secure you can obviously keep the password in the code as well. However, you want the flexibility of being able to change the credentials without changing the code.

如果您能保证代码的安全,您显然也可以将密码保存在代码中。但是,您希望能够灵活地更改凭据而不更改代码。

You can add more layers to this solution as well. You can encrypt the configuration file (with a different key) as well as the password inside it making the hacker discover 2 keys. There are other even more secure methods using PKI, but they get hard to set up.

您也可以向此解决方案添加更多层。您可以加密配置文件(使用不同的密钥)以及其中的密码,让黑客发现 2 个密钥。还有其他使用 PKI 的更安全的方法,但它们很难设置。

回答by Mike McAllister

I'd suggest you look into proxy authentication. This is documented in the Oracle? Database Security Guide, as well as the Oracle? Database JDBC Developer's Guide and Reference. Essentially what this allows you to do is have a user in the database that ONLY has connect privileges. The users real database accounts are configured to be able connect as the proxy user. Your application connecting through JDBC then stores the proxy username and password, and when connecting provides these credentials, PLUS the username of the real database user in the connect string. Oracle connects as the proxy user, and then mimics the real database user, inheriting the database privileges of the real user.

我建议您研究代理身份验证。这在oracle中有记载吗?数据库安全指南,还有Oracle?数据库 JDBC 开发人员指南和参考。本质上,这允许您做的是在数据库中拥有一个仅具有连接权限的用户。用户真实数据库帐户被配置为能够作为代理用户连接。您通过 JDBC 连接的应用程序然后存储代理用户名和密码,并且在连接时提供这些凭据,以及连接字符串中真实数据库用户的用户名。Oracle以代理用户的身份连接,然后模仿真实的数据库用户,继承真实用户的数据库权限。

回答by Achille

All J2EEcontainers (JBOSS, Tomcat, BEA) have connection pools. They will open a number of connections, keep them alive and will give them to you in 1/100ththe time it takes to create one from scratch.

所有J2EE容器(JBOSSTomcatBEA)都有连接池。他们将打开的连接数,让他们活着,并把它们给你1/100需要创建一个从头开始的时间。

Additionally, they also have cool features, in JBOSSfor example, all the connection info is stored in an external file. If you change the connection info i.e., you switch from a testto a productionDB, your application will dynamically be fed connections from the new pool

此外,它们还有很酷的功能,JBOSS例如,所有连接信息都存储在一个外部文件中。如果您更改连接信息,即从测试切换到生产数据库,您的应用程序将动态地从新池中获取连接

The good news is that you don't need to run a full J2EEcontainer just to use connection pooling. The external resource allows the password to be stored in either plaintext, or pseudo-encrypted.

好消息是你不需要运行一个完整的J2EE容器来使用连接池。外部资源允许以明文或伪加密方式存储密码。

For a guide on using Tomcat's builtin connection pooling see the apache commons-dbcp:

有关使用 Tomcat 的内置连接池的指南,请参阅 apache commons-dbcp:

回答by Martin Spamer

There are two key approaches and both have a significant impact on the design of the system, such that it is not easy to move from one to the other without a significant rewrite. You need to understand what your companies security governance policy is before choosing.

有两种关键方法,它们都对系统的设计产生重大影响,因此如果不进行大量重写,就不容易从一种方法移动到另一种方法。在选择之前,您需要了解您公司的安全治理策略是什么。

1) Every user has credentials, that are carried through the application, for the service that is being used by the Application; in your case the Oracle database uses those user credentials to connect to the database. The downside is that every user needs a credentials for each secure service. This is a reasonable secure approach but also requires the signficant extra work to provide and maintain the user credentials. Your database administrators will need to actively manage user credentials, which may run counter to your company's security governance policies.

1) 每个用户都拥有通过应用程序携带的应用程序正在使用的服务的凭据;在您的情况下,Oracle 数据库使用这些用户凭据连接到数据库。缺点是每个用户都需要每个安全服务的凭据。这是一种合理的安全方法,但也需要大量的额外工作来提供和维护用户凭据。您的数据库管理员将需要主动管理用户凭据,这可能与您公司的安全治理策略背道而驰。

2) The Application database credentials are stored on a secure directory service, e.g. Secure LDAP. The Application accesses the directory service with the users' credentials. The directory service returns the approriate credentials for the service being accessed.

2) 应用程序数据库凭据存储在安全目录服务中,例如安全 LDAP。应用程序使用用户的凭据访问目录服务。目录服务返回所访问服务的适当凭证。

In both cases the database credentials should be limited to perform the appropriate operations only. The credentials should reflect the requirements of the business processes, for example; they allow select from defined views/tables, insert into others, but not create, update or drop tables. In the second approach use seperate credentials for each major business process, e.g. Order Processing, Accounting, HR, etc.

在这两种情况下,数据库凭据都应仅限于执行适当的操作。例如,凭证应反映业务流程的要求;它们允许从定义的视图/表中进行选择,插入到其他视图中,但不能创建、更新或删除表。在第二种方法中,对每个主要业务流程使用单独的凭证,例如订单处理、会计、人力资源等。

However remember that security is like layers of an onion, if somebody has stripped away the layers to access the application, such that they can access the DB contection pool config file. They can probably Trojan the application to capture users' credentials. This is where a good security governance policy comes in.

但是请记住,安全就像一层一层的洋葱,如果有人剥离了这些层来访问应用程序,这样他们就可以访问数据库连接池配置文件。他们可能会特洛伊木马应用程序以捕获用户的凭据。这就是良好的安全治理策略的用武之地。

Security Governance is a complex issue that needs senior management commitment, because if you need this level of security for your live platform, it costs. You need to separate responsibilities of development from deployment, operations & user authority management. You may also need to have security auditors, who have full access to view changes but no ability to change the configuration. It if far from simple and is highly paid specialism.

安全治理是一个复杂的问题,需要高级管理层做出承诺,因为如果您的实时平台需要这种级别的安全性,则需要付出代价。您需要将开发职责与部署、运营和用户权限管理分开。您可能还需要安全审核员,他们拥有查看更改的完全访问权限,但无权更改配置。它远非简单而且是高薪专业。

回答by curtisk

Since I'm not entirely clear on your environment other than Java & JDBC talking to Oracle I'll speak towards that.

由于除了 Java 和 JDBC 与 Oracle 交谈之外,我对您的环境并不完全清楚,因此我将对此进行讨论。

If you are talking about a Java EE app, you should be able to setup connection pools and data sources on the app server, then your application talks to the connection pool who handles connectivity at that level.

如果您在谈论 Java EE 应用程序,您应该能够在应用程序服务器上设置连接池和数据源,然后您的应用程序与处理该级别连接的连接池进行对话。

The connection pool and data source holds and secures the credentials.

连接池和数据源保存并保护凭据。

回答by kosoant

To my knowledge jdbc connection usernames/passwords need to be stored as plain text. One way to limit the possible risks of this is to restrict the rights of the user so that only the given applications database can be used and only from a predefined host. IMO, this would limit the attacker very much: he could only use the un/pw from the same host where the original application resides and only to attack the original application's database.

据我所知 jdbc 连接用户名/密码需要存储为纯文本。限制这种可能风险的一种方法是限制用户的权限,以便只能使用给定的应用程序数据库并且只能从预定义的主机使用。IMO,这将极大地限制攻击者:他只能使用来自原始应用程序所在的同一主机的 un/pw,并且只能攻击原始应用程序的数据库。

回答by JeeBee

Have wondered this in the past.

过去曾想过这个问题。

The solution is certainly one that includes having proper network security at the server and network level to really reduce the number of people who can get access to the system, and having the database credentials only give access to a database account with the bare minimum of permissions required for the application to run.

解决方案当然是包括在服务器和网络级别拥有适当的网络安全以真正减少可以访问系统的人数,并拥有数据库凭据仅允许访问具有最低权限的数据库帐户应用程序运行所必需的。

Encryption of properties files might be enough of a deterrent in terms of "can't be bothered to find the key or passphrase" to get an attacker to go onto their next compromised server. I wouldn't rely on "my neighbour is less secure so steal from him please" security however!

属性文件的加密可能足以阻止“无需费心寻找密钥或密码短语”来让攻击者进入他们的下一个受感染服务器。然而,我不会依赖“我的邻居不太安全,所以请从他那里偷东西”的安全性!

回答by Alexander

You could try Oracle's proxy authentication where the JDBC client authenticates using a certificate against a known middle-tier component/service (the proxy) which is trusted by the database server. I've never tried that though, so I don't know whether it's easy to do.

您可以尝试 Oracle 的代理身份验证,其中 JDBC 客户端使用证书针对数据库服务器信任的已知中间层组件/服务(代理)进行身份验证。不过我从来没有尝试过,所以我不知道这是否容易做到。

回答by Hank Gay

You can store the credentials anywhere, including as hardwired strings in the program or as entries in the Windows registry. It's up to you to retrieve them if you use something nonstandard, though; I'm not aware of any pre-rolled solutions that aren't plaintext.

您可以将凭据存储在任何位置,包括作为程序中的硬连线字符串或作为 Windows 注册表中的条目。但是,如果您使用非标准的东西,则由您来检索它们;我不知道任何非明文的预卷解决方案。