Appendix I - Java 17 upgrade and changes introduced with 7.2311.0.x
Together with Java 17 upgrade, a major cleanup was done in multiple places including the update of most dependencies. This appendix will guide you through the changes.
It is recommended to recompile custom Java auth states, REST or SOAP services using Java 17 and nevisAuth artifacts version 7.2311.x. As all of those are likely to become incompatible.
Note, that recompilation does not warrant that everything will work fine. Even if the build is successful, runtime issues can still arise. Therefore, thorough testing of any custom development is recommended.
Nevis does not recommend and will not provide support for using Java 8 compiled custom Java auth states, REST or SOAP services in nevisAuth version 7.2311.x.
nevisAuth API changes
The following chapter summarizes the changes in the nevisAuth SDK.
The following list does not contain every change made in the internal artifact nevisauth-core or other modules.
Date handling
Java 8 introduced a new java.time API which replaces the old legacy API (java.util.Date, java.utils.Calendar and more)
The community and industry seems to be lagging behind with introducing the new java.time API. This is caused by Java API itself using the legacy date API in core places, because it is very difficult to replace.
Third party libraries used by nevisAuth start to use the java.time API more and more. Therefore, Nevis also moved on to use the java.time API. This causes breaking changes in multiple places of the nevisAuth API.
As the date handling is quite complex, the separate Date Handling Changes guide you through the changes there.
OOCD
Changes in the OOCD interface because of the date handling and removing deprecated API & features. For more see OOCD Changes.
Session
| Where | Old | Replacement |
|---|---|---|
NevisSession | getAttributeNames | getAttributeNamesIterator |
NevisSession | acquireReadOnly | ❌ |
NevisSession | acquireReadWrite | - (moved to Session) |
NevisSession | release | - (moved to Session) |
NevisSession | Object getData(); | Map<String, String> getData(); |
NevisSession | Object getAttribute(String name); | String getAttribute(String name); |
NevisSession | void setAttribute(String name, Object value); | void setAttribute(String name, String value); |
Session | isInitial | isAuthentic Note it is the inverse! |
Session | getDomainMappings | ❌ |
Session | setDomainMappings | ❌ |
ScriptState | Map<?,?> session | Map<String,String> session |
ScriptStates
The change that the Session attributes are only accepting String has a special caveat in Groovy scripts.
Groovy itself does not enforce types strictly on a Map object; thus in a groovy script, you can actually set a non String object in a String typed Map. This behaviour causes a ClassCastException in nevisAuth when the Session is accessed from the Java code.
To mitigate this the ScriptState will check the session attributes for any non String values and throw an exception with the name of the keys and types.
A special case of this is when a org.codehaus.groovy.runtime.GStringImpl type is added as a Session attribute. This happens when using an expression inside double quotes. Example: session.put("outarg.$name", value) working replacement: session.put('outarg.' + name, value).
Below is an example of how to convert non String objects to JSON to store it in the session. Based on our experience, the most typical case is when a script try to store a Map object in the session. In some cases a simple concatenation could also work - but using the JSON utilities from Groovy reduces the chance of an error. (You don't have to worry about escaping.) As serialisation is a complex topic, this approach might not work with more complex Java types.
import groovy.json.JsonOutput
import groovy.json.JsonSlurper
def originalMap = [
key1: 'value1',
key2: 'value2'
]
session.put('test', JsonOutput.toJson(originalMap));
def restoredMap = new JsonSlurper().parseText(session['test'])
In previous versions nevisAuth did not store non String session attributes in the remote session store. When migrating to store session attributes in String format in your scripts, mind that now nevisAuth also stores those in the database. In case you just temporarily stored some objects in the session and relied on the remote session store to throw them away, now you have to take care of removing those from the session yourself. (If those are not to be stored in the session on the long term.)
AuthEngine / AuthState general
| Where | Old | Replacement |
|---|---|---|
AuthConst | DEFAULT_TRANSITION | DEFAULT_RESULT |
AuthConst | LAST_TRANSITION | LAST_RESULT |
AuthConst | LAST_STATE | CURRENT_STATE |
AuthConst | INVALID_INPUT | AUTH_FAILED |
AuthConst | NEVIS_AUTH_GUI | ❌ |
AuthState | isInitialDispatcher | ❌ |
AuthState | getAttribute | getMandatoryAttribute or getOptionalAttribute |
AuthState | convertListDescriptor | getListAttribute |
AuthState | getHttpHeaderFromRequest | request.getHttpHeader |
AuthState | getTransition | getTransition with AuthRequest and AuthResponse parameters |
AuthTransition | getName | getTriggeringCondition |
AuthTransition | getState | getTargetState |
AuthRequest | getDomainMapping | ❌ |
AuthRequest | getDomainMappings | ❌ |
AuthResponse | setDomainMappings | ❌ |
AuthResponse | addDomainMapping | ❌ |
Auditable | getDomainMappings | ❌ |
EL expression | addDomainMapping | ❌ |
Utilities
| Old | Replacement |
|---|---|
CommandStarter, CommandWaiter, StreamConnector | CommandExecutor |
deprecated encryptWhereNeccessary method in the Communicator, Encrypter | encryptWhereNeccessary with additional arguments |
AuthSSLContextFactory | ❌ |
AuthSSLX509TrustManager | ❌ |
Command line utilities in jcan-saml | ❌ |
SAML Assertion / Response generation signing in jcan-saml | Use OpenSaml 4. |
jcan-saml-tools.jar | ❌ |
Command line utilities in jcan-sectoken | ❌ |
Deprecated methods in jcan-sectoken | ❌ |
OpTracing
Implementation
The old library jcan-optrace relies on the javax.servlet API, therefore it is not compatible with the new Java 17 nevisAuth release.
As Nevis does not have the source of this library the jcan.Op OpTrace logs will be replaced by using OpenTelemetry Java agent.
Default behaviour
By default, the nevisAuth RPM package does not contain the binaries or configuration for OpenTelemetry therefore by default there is no OpTrace. To set up OpenTelemetry check out the guide here.
Configuration
OpenTelemetry requires Java agent configuration in the env.conf and its own configuration file, see the guide for more.
Configuration changes
OOCD
Changes in the OOCD configuration to unify the database related configurations in nevisAuth. For more see Appendix K.
esauth4.xml
Property changes
| Where | Old | Replacement |
|---|---|---|
RemoteSessionStore | connectionMaxRetry | ❌ |
SendMail & Tan | smtpHost | mail.smtp.host |
SendMail & Tan | smtpPort | mail.smtp.port |
esauth-server | securityLevel | ❌ |
X509Login | crlExpirationTolerance | revocationCheckExpirationTolerance |
Property value changes
| Where | Property | Change |
|---|---|---|
RemoteSessionStore | provider | legacyjdbc provider option removed |
RemoteSessionStore | sessionIdRandomBytes | custom class support using "file://..." removed |
SecurityTokenServiceClient RadiusAuthState MobileSignatureState | service.binding | session option removed |
env.conf JAVA_OPTS
JVM system properties from Java
Some JVM system properties are discontinued in Java:
-XX:+UseConcMarkSweepGC-XX:+UseParNewGC
There might be others, we don't have a complete list of those. In case you have a no longer supported JVM system property you will encounter an error like this:
Sep 05 09:13:01 10a605af06ed nevisauth-server[2026]: Unrecognized VM option 'UseConcMarkSweepGC'
Sep 05 09:13:01 10a605af06ed nevisauth-server[2026]: Error: Could not create the Java Virtual Machine.
Sep 05 09:13:01 10a605af06ed nevisauth-server[2026]: Error: A fatal exception has occurred. Program will exit.
The error message above will be present in the system out therefore in the systemd journal. As the process fails before logging could be set up.
System properties can be removed because of turned on by default:
-server-> default on 64bit vms-XX:+UseContainerSupport-> default true
Nevis system properties
The following properties can be removed:
-Dch.nevis.bc.io.TracerCfgrelated to the logging framework, not used.-Dch.nevis.tracing.refreshrelated to the logging framework, not used.-Djava.security.krb5.confthe new KerberosLogin auth state does not support impersonation/delegation, so it is not a “Kerberos client” anymore.-Dch.nevis.esauth.litdict.charset.encodingBy default nevisAuth uses UTF-8. In case you have your litdict files UTF-8 encoded (which they should be) it is not necessary to define this.-Dch.nevis.esauth.wstrust.SecurityTokenService.SecTokenHackURIold backwards compatibility flag.
Java 17 API changes
This chapter contains the non nevisAuth specific changes caused by upgrading Java to version 17.
Java modules (JPMS)
nevisAuth and the authentication components do not define any Java modules JPMS. Components rely on the automatic unnamed module handling of Java. This is a backwards compatibility feature allowing access to all codebase as before Java 9 when there was no JPMS.
Introducing JPMS would cause severe restrictions on what can be accessed from the nevisAuth codebase, therefore custom Java auth states developed by customers would no longer be able to access code from the nevisauth-core jar, only nevisauth-authstate-api and nevisauth-commons.
Accessing code from nevisauth-core is already considered a bad practice and is done at your own risk. Though we are aware that because of historical reasons many rely on nevisauth-core.
We recommend using the offical SDK which is shipped in the nevisauth rpm package and mainly consist of the nevisauth-authstate-api and nevisauth-commons.
In the future, JPMS modules will be introduced at some point which will probably require additions to our SDK, however without our knowledge of what customers exactly require there will be no extensions.
Therefore, again we recommend customers currently relying on nevisauth-core to try to use the SDK and inform us via the official support channels if something is missing.
Java internal packages
Even though nevisAuth itself does not define JPMS modules, Java 17 already have modules itself. You can no longer access Java packages which are considered to be internal by Java itself.
In case you used a Java internal package which is no longer public, you will receive a compile error. In certain cases for example reflection usage might be only spotted at runtime.
Internal Java modules/packages we encountered in the nevisAuth during the Java 17 migration (this is not a complete list of all Java internal modules):
- java.security.jgss/sun.security.krb5
- java.security.jgss/sun.security.krb5.internal
- java.security.jgss/sun.security.krb5.internal.ccache
- java.security.jgss/sun.security.jgss
- java.security.jgss/sun.security.jgss.krb5
- java.base/sun.security.provider
- java.base/sun.security.util
- java.base/sun.security.pkcs
- java.base/sun.security.x509
Some of the security features can be accessed via the java.security package. Though it does not expose the whole feature set previously available via sun.security. In some cases you might have to find replacement implementations for example using Bouncy Castle.
It is also possible to encounter a third party dependency which uses Java internal API and because of that you can no longer use it. These typically only surface at runtime. Unless you use the --add-exports command line option and specify a module/package to force Java to expose that internal API. The --add-exports option is a last resort for backwards compatibility, it is not recommended and not clear how long will be available. At Nevis we used this approach in our unit testing setup in one case, where Mockserver uses internal Java API for dealing with X509 certificates. You can find the example for this in the pom.xml in the SDK example project in the RPM.
Nevis cannot provide support for replacing Java internal package usages in custom auth states.
Nevis does not recommend and support the usage of --add-exports parameters to make internal Java API publicly available in production code.
SubjectDN and IssuerDN
Java X509Certificate.getSubjectDN() and X509Certificate.getIssuerDN() method are deprecated.
The method getSubjectDN().getName() used a non-standard format for getting the String DN representation (This comes from Java). It was used in multiple places in nevisAuth and possibly also in custom auth states or groovy scripts.
To remain backwards compatible we use X509Certificate.getSubjectX500Principal().toString() which uses the same formatting as the old one. Note that X509Certificate.getSubjectX500Principal().getName() will use RFC-2253 formatting, which is different from the non-standard format.
The following auth states are affected:
- X509Login
- MobileSignatureState (special because the SubjectDN is stored in nevisIdm)
- WSSHeaderValidation
- SAML
Additionally, certificate handling in general and the SecurityTokenService. Furthermore, the non-standard RDN attribute separator / is no longer supported in the X509Login.
Default encoding
We noticed changes of the default encoding in some places in from ISO-8559-1 to UTF-8 which is the Java 17 default. We are not aware of the extent of these changes in Java itself or third party libraries. Based on our testing nevisAuth is not affected, because in most cases the encoding can be configured, so the Java default value does not matter. So far we are only aware of nevisLogRend being affected. However, there is a possibility that we did not notice some parts which may be affected.
Furthermore, it is possible that in custom auths states this default value change causes encoding errors, which can be fixed by either providing the desired encoding or changing the encoding to UTF-8.