I need to use Container Managed Security and Authentication in my latest project. And I have a couple of queries regarding how to configure a Credential Handler.
MessageDigestCredentialHandler
and
SecretKeyCredentialHandler
which one is more secure ?SecretKeyCredentialHandler
specifies only one algorithm in the
documentation which is PBKDF2WithHmacSHA1
. What other algorithms are
available ?It is a simple XML file; the root element is tomcat-users and the only allowed child elements are role and user . Each role element has one attribute called rolename , and each user element has three attributes: name , password , and roles . The default tomcat-users. xml file contains the XML listed in Example 7-3.
Tomcat 9: Manager Access with Username/Passowrd In addition to that, rhere is no default username and password. To enable this access, you must create a new username/password combination and associate it with the manager-gui role (list below). To do this, you'll need to modify the $CATALINA_BASE/conf/tomcat-users.
A Tomcat valve - a new technology introduced with Tomcat 4 which allows you to associate an instance of a Java class with a particular Catalina container. This configuration allows the named class to act as a preprocessor of each request. These classes are called valves, and they must implement the org. apache.
To answer the first point, here's a comparison of the <Realm>
from my context.xml before and after the switch to Tomcat 8:
Before:
<Realm className="org.apache.catalina.realm.DataSourceRealm"
dataSourceName="jdbc/myDataSource"
roleNameCol="role" userCredCol="password" userNameCol="loginid"
digest="md5"
userRoleTable="userroles" userTable="users"
localDataSource="true" />
After:
<Realm className="org.apache.catalina.realm.DataSourceRealm"
dataSourceName="jdbc/myDataSource"
roleNameCol="role" userCredCol="password" userNameCol="loginid"
userRoleTable="userroles" userTable="users" localDataSource="true">
<CredentialHandler
className="org.apache.catalina.realm.MessageDigestCredentialHandler"
algorithm="md5" />
</Realm>
NestedCredentialHandler is for cases when you have multiple digest methods, for example you have used MessageDigest in the past but now you want to switch a more secure PBKDF2-SHA512 configuration, and don't want to make already configured passwords invalid.
For example:
<CredentialHandler className="org.apache.catalina.realm.NestedCredentialHandler">
<CredentialHandler className="org.apache.catalina.realm.SecretKeyCredentialHandler"
algorithm="PBKDF2WithHmacSHA512"
iterations="100000"
keyLength="256"
saltLength="16"
/>
<CredentialHandler className="org.apache.catalina.realm.MessageDigestCredentialHandler"
algorithm="SHA-256"
iterations="1000"
keyLength="256"
saltLength="8"
/>
</CredentialHandler>
<!-- NOTE: keyLength is in bits, saltLength is in bytes. 16 bytes = 128 bits -->
This would go inside your Realm element.
SecretKeyCredentialHandler was introduced in Tomcat 8.0.15 and uses SecretKeyFactory from the javax.crypto API rather than the old method (MessageDigest) to mutate the password. SecretKeyFactory allows for better algorithms such as PBKDF2 with HMAC-SHA-512 rather than plain hash algorithms such as SHA-512. The old method is since available via MessageDigestCredentialHandler, which is equivalent of setting the digest attribute on the Realm element directly.
Please note, setting the digest attribute directly or using MessageDigestCredentialHandler without the optional iteration attribute (8.0.15+ only) will only do one iteration. This is NOT secure.
As for what algorithms are available for SecretKeyFactory, the Java Cryptography Architecture Standard Algorithm Name Documentation for JDK 8 is the best reference I could find, but it doesn't list all combinations explicitly. These were the ones I found working on my platform (Linux 3.13.0, Oracle JDK 1.8.0_111), but yours may support other combinations.
I have a requirement to deploy the same myapp.war binary file to Tomcat7 and Tomcat8 environments. Using this configuration both environments work fine.
myapp/META-INF/context.xml
<Realm className="org.apache.catalina.realm.DataSourceRealm"
dataSourceName="jdbc/myapp" localDataSource="true" digest="SHA-256"
userTable="user_role_v" userNameCol="username" userCredCol="password"
userRoleTable="user_role_v" roleNameCol="role">
<CredentialHandler className="org.apache.catalina.realm.MessageDigestCredentialHandler"
algorithm="SHA-256" iterations="1" saltLength="0" encoding="ISO-8859-1" />
</Realm>
You see a warning in catalina log file at startup for unknown parameter but it does not matter.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With