Skip to content

Commit dca7a58

Browse files
committed
Introduce AuthToken rotation and session auth support
The main feature of this update is the support for `AuthToken` rotation, which might also be referred to as a refresh or re-auth. In practice, it allows replacing the current token with a new token during the driver's lifetime. The main objective of this feature is to allow token rotation for the same identity. As such, it is not intended for a change of identity. A new type called `AuthTokenManager` has the following 2 primary responsibilities: - supplying a valid token, which may be one of the following: - the current token - a new token, which instructs the driver to use the new token - handling a token expiration failure that originates from the server if it determines the current token to be expired (a timely rotation should generally reduce the likelihood of this happening) The driver does not make judgements on whether the current `AuthToken` should be updated. Instead, it calls the `AuthTokenManager` to check if the provided token is the same as the currently used token and takes action if not. The driver reserves the right to call the manager as often as it deems necessary. The manager implementations must be thread-safe and non-blocking for caller threads. For instance, IO operations must not be done on the calling thread. The `GraphDatabase` class has been updated to include a set of new methods that accept the `AuthTokenManager`. An example of the driver instantiation: ```java var manager = // the manager implementation var driver = GraphDatabase.driver(uri, manager); ``` The token rotation benefits from the new Bolt 5.1 version, but works on previous Bolt versions at the expence of replacing existing connections with new connections. An expiration based `AuthTokenManager` implementation is available via a new `AuthTokenManagers` factory. It manages `AuthToken` instances that come with a UTC expiration timestamp and calls a new token supplier, which is provided by the user, when a new token is required. An example of the expiration based manager instantiation: ```java var manager = AuthTokenManagers.expirationBased(() -> { var token = // get new token logic return token.expiringAt(timestamp); // a new method on AuthToken introduced for the supplied expiration based AuthTokenManager implementation }); ``` The new `LOGOFF` and `LOGON` Bolt protocol messages allow for auth management on active Bolt connections and are used by the features in this update. In addition to the token rotation support, this update also includes support for setting a static `AuthToken` instance on the driver session level. Unlike the rotation feature, this feature may be used for an identity change. As such, it might be referred to as user switching. It requires a minimum Bolt 5.1 version. The `Driver` interface has 2 new `session` methods that accept an `AuthToken` instance. A basic example: ```java var token = AuthTokens.bearer("token"); var session = driver.session(Session.class, token); ``` The `Driver` includes a new method that checks whether the session auth is supported. The implementation assumes all servers to be at the same version. Sample usage: ```java var supports = driver.supportsSessionAuth(); ``` The `Driver` includes a new method that verifies a given `AuthToken` instance by communicating with the server. It requires a minimum Bolt 5.1 version. Sample usage: ```java var token = AuthTokens.bearer("token"); var successful = driver.verifyAuthentication(token); ``` There are 2 new exceptions: - `AuthTokenManagerExecutionException` - Indicates that the `AuthTokenManager` execution has lead to an unexpected result. This includes invalid results and errors. - `TokenExpiredRetryableException` - Indicates that the token supplied by the `AuthTokenManager` has been deemed as expired by the server. This is a retryable variant of the `TokenExpiredException` used when the driver has an explicit `AuthTokenManager` that might supply a new token following this failure. If driver is instantiated with the static `AuthToken`, the `TokenExpiredException` will be used instead.
1 parent cbc54bc commit dca7a58

File tree

159 files changed

+7071
-508
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

159 files changed

+7071
-508
lines changed

bundle/pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
<parent>
77
<groupId>org.neo4j.driver</groupId>
88
<artifactId>neo4j-java-driver-parent</artifactId>
9-
<version>5.7-SNAPSHOT</version>
9+
<version>5.8-SNAPSHOT</version>
1010
<relativePath>..</relativePath>
1111
</parent>
1212

bundle/pom.xml.versionsBackup

Lines changed: 273 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,273 @@
1+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
2+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
3+
http://maven.apache.org/xsd/maven-4.0.0.xsd">
4+
<modelVersion>4.0.0</modelVersion>
5+
6+
<parent>
7+
<groupId>org.neo4j.driver</groupId>
8+
<artifactId>neo4j-java-driver-parent</artifactId>
9+
<version>5.7-SNAPSHOT</version>
10+
<relativePath>..</relativePath>
11+
</parent>
12+
13+
<artifactId>neo4j-java-driver-all</artifactId>
14+
15+
<packaging>jar</packaging>
16+
<name>Neo4j Java Driver (shaded package)</name>
17+
<description>Access to the Neo4j graph database through Java</description>
18+
<url>https://github.com/neo4j/neo4j-java-driver</url>
19+
20+
<properties>
21+
<moduleName>org.neo4j.driver</moduleName>
22+
<rootDir>${project.basedir}/..</rootDir>
23+
<maven.compiler.xlint.extras>,-try</maven.compiler.xlint.extras>
24+
<maven.deploy.skip>false</maven.deploy.skip>
25+
</properties>
26+
27+
<dependencies>
28+
<!-- The original driver that will be repackaged. -->
29+
<dependency>
30+
<groupId>org.neo4j.driver</groupId>
31+
<artifactId>neo4j-java-driver</artifactId>
32+
<version>${project.version}</version>
33+
<optional>true</optional>
34+
</dependency>
35+
36+
<!-- Optional and / or provided dependencies, as they are not transitive to the original driver they must be declared again. -->
37+
<dependency>
38+
<groupId>io.micrometer</groupId>
39+
<artifactId>micrometer-core</artifactId>
40+
<optional>true</optional>
41+
</dependency>
42+
<dependency>
43+
<groupId>org.slf4j</groupId>
44+
<artifactId>slf4j-api</artifactId>
45+
<optional>true</optional>
46+
</dependency>
47+
<dependency>
48+
<groupId>org.graalvm.nativeimage</groupId>
49+
<artifactId>svm</artifactId>
50+
</dependency>
51+
52+
<!-- As we pretend the driver being provided only, we need be explicit about the one dependency we actually didn't shade. -->
53+
<dependency>
54+
<groupId>org.reactivestreams</groupId>
55+
<artifactId>reactive-streams</artifactId>
56+
</dependency>
57+
</dependencies>
58+
59+
<build>
60+
<pluginManagement>
61+
<plugins>
62+
<plugin>
63+
<groupId>org.apache.maven.plugins</groupId>
64+
<artifactId>maven-javadoc-plugin</artifactId>
65+
<executions>
66+
<execution>
67+
<id>attach-javadocs</id>
68+
<goals>
69+
<goal>jar</goal>
70+
</goals>
71+
<configuration>
72+
<additionalOptions combine.children="append">
73+
<option>--add-exports org.graalvm.sdk/com.oracle.svm.core.annotate=org.neo4j.driver</option>
74+
</additionalOptions>
75+
</configuration>
76+
</execution>
77+
</executions>
78+
</plugin>
79+
</plugins>
80+
</pluginManagement>
81+
<plugins>
82+
<!-- Extract the original sources again -->
83+
<plugin>
84+
<groupId>org.apache.maven.plugins</groupId>
85+
<artifactId>maven-resources-plugin</artifactId>
86+
<version>3.2.0</version>
87+
<executions>
88+
<execution>
89+
<id>copy-appCtx</id>
90+
<phase>generate-sources</phase>
91+
<goals>
92+
<goal>copy-resources</goal>
93+
</goals>
94+
<configuration>
95+
<outputDirectory>${project.build.directory}/generated-sources/neo4j-java-driver</outputDirectory>
96+
<overwrite>true</overwrite>
97+
<resources>
98+
<resource>
99+
<directory>${rootDir}/driver/src/main/java</directory>
100+
<includes>
101+
<include>**\/*.java</include>
102+
</includes>
103+
</resource>
104+
</resources>
105+
</configuration>
106+
</execution>
107+
</executions>
108+
</plugin>
109+
<!-- Attach them -->
110+
<plugin>
111+
<groupId>org.codehaus.mojo</groupId>
112+
<artifactId>build-helper-maven-plugin</artifactId>
113+
<executions>
114+
<execution>
115+
<id>attach-original-sources</id>
116+
<phase>generate-sources</phase>
117+
<goals>
118+
<goal>add-source</goal>
119+
</goals>
120+
<configuration>
121+
<sources>
122+
<source>${project.build.directory}/generated-sources/neo4j-java-driver</source>
123+
</sources>
124+
</configuration>
125+
</execution>
126+
<execution>
127+
<id>set-osgi-version</id>
128+
<phase>validate</phase>
129+
<goals>
130+
<goal>parse-version</goal>
131+
</goals>
132+
</execution>
133+
</executions>
134+
</plugin>
135+
<plugin>
136+
<groupId>org.apache.maven.plugins</groupId>
137+
<artifactId>maven-source-plugin</artifactId>
138+
</plugin>
139+
<plugin>
140+
<groupId>org.apache.maven.plugins</groupId>
141+
<artifactId>maven-javadoc-plugin</artifactId>
142+
</plugin>
143+
<plugin>
144+
<groupId>org.apache.maven.plugins</groupId>
145+
<artifactId>maven-jar-plugin</artifactId>
146+
<executions>
147+
<execution>
148+
<goals>
149+
<goal>test-jar</goal>
150+
</goals>
151+
</execution>
152+
</executions>
153+
<configuration>
154+
<archive>
155+
<index>true</index>
156+
<manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
157+
<manifest>
158+
<packageName>org/neo4j/driver</packageName>
159+
</manifest>
160+
<manifestEntries>
161+
<!-- This is used to programmatically determine the driver version -->
162+
<Implementation-Version>${project.version}-${build.revision}</Implementation-Version>
163+
<!-- Stable module name for JDK9 automatic modules -->
164+
<Automatic-Module-Name>${moduleName}</Automatic-Module-Name>
165+
</manifestEntries>
166+
</archive>
167+
</configuration>
168+
</plugin>
169+
<plugin>
170+
<groupId>org.apache.felix</groupId>
171+
<artifactId>maven-bundle-plugin</artifactId>
172+
<extensions>true</extensions>
173+
</plugin>
174+
<plugin>
175+
<groupId>org.apache.maven.plugins</groupId>
176+
<artifactId>maven-shade-plugin</artifactId>
177+
<executions>
178+
<execution>
179+
<phase>package</phase>
180+
<goals>
181+
<goal>shade</goal>
182+
</goals>
183+
<configuration>
184+
<artifactSet>
185+
<includes>
186+
<include>io.netty:*</include>
187+
<include>io.projectreactor:*</include>
188+
</includes>
189+
</artifactSet>
190+
<relocations>
191+
<relocation>
192+
<pattern>io.netty</pattern>
193+
<shadedPattern>org.neo4j.driver.internal.shaded.io.netty</shadedPattern>
194+
</relocation>
195+
<relocation>
196+
<pattern>reactor</pattern>
197+
<shadedPattern>org.neo4j.driver.internal.shaded.reactor</shadedPattern>
198+
</relocation>
199+
</relocations>
200+
<transformers>
201+
<transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer"/>
202+
</transformers>
203+
<filters>
204+
<filter>
205+
<artifact>io.netty:*</artifact>
206+
<excludes>
207+
<exclude>META-INF/native-image/**</exclude>
208+
</excludes>
209+
</filter>
210+
<filter>
211+
<artifact>${groupId}:${artifactId}</artifact>
212+
<excludes>
213+
<exclude>module-info.java</exclude>
214+
</excludes>
215+
</filter>
216+
</filters>
217+
<shadeTestJar>true</shadeTestJar>
218+
<createSourcesJar>true</createSourcesJar>
219+
</configuration>
220+
</execution>
221+
</executions>
222+
</plugin>
223+
<plugin>
224+
<groupId>org.apache.maven.plugins</groupId>
225+
<artifactId>maven-antrun-plugin</artifactId>
226+
<executions>
227+
<execution>
228+
<id>add-module-info-to-sources</id>
229+
<phase>package</phase>
230+
<goals>
231+
<goal>run</goal>
232+
</goals>
233+
<configuration>
234+
<target>
235+
<unzip src="${project.build.directory}/${artifactId}-${version}-sources.jar" dest="${project.build.directory}/sources-with-module"/>
236+
<copy file="${project.basedir}/src/main/jpms/module-info.java" tofile="${project.build.directory}/sources-with-module/module-info.java" />
237+
<zip basedir="${project.build.directory}/sources-with-module" destfile="${project.build.directory}/${artifactId}-${version}-sources.jar"/>
238+
</target>
239+
</configuration>
240+
</execution>
241+
</executions>
242+
</plugin>
243+
<plugin>
244+
<groupId>org.moditect</groupId>
245+
<artifactId>moditect-maven-plugin</artifactId>
246+
<executions>
247+
<execution>
248+
<id>add-module-infos</id>
249+
<phase>package</phase>
250+
<goals>
251+
<goal>add-module-info</goal>
252+
</goals>
253+
<configuration>
254+
<overwriteExistingFiles>true</overwriteExistingFiles>
255+
<module>
256+
<moduleInfoFile>
257+
${basedir}/src/main/jpms/module-info.java
258+
</moduleInfoFile>
259+
</module>
260+
</configuration>
261+
</execution>
262+
</executions>
263+
</plugin>
264+
</plugins>
265+
</build>
266+
267+
<scm>
268+
<connection>scm:git:git://github.com/neo4j/neo4j-java-driver.git</connection>
269+
<developerConnection>scm:git:[email protected]:neo4j/neo4j-java-driver.git</developerConnection>
270+
<url>https://github.com/neo4j/neo4j-java-driver</url>
271+
</scm>
272+
273+
</project>

driver/clirr-ignored-differences.xml

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -503,4 +503,34 @@
503503
<method>org.neo4j.driver.BookmarkManager executableQueryBookmarkManager()</method>
504504
</difference>
505505

506+
<difference>
507+
<className>org/neo4j/driver/Driver</className>
508+
<differenceType>7012</differenceType>
509+
<method>org.neo4j.driver.BaseSession session(java.lang.Class, org.neo4j.driver.AuthToken)</method>
510+
</difference>
511+
512+
<difference>
513+
<className>org/neo4j/driver/Driver</className>
514+
<differenceType>7012</differenceType>
515+
<method>org.neo4j.driver.BaseSession session(java.lang.Class, org.neo4j.driver.SessionConfig, org.neo4j.driver.AuthToken)</method>
516+
</difference>
517+
518+
<difference>
519+
<className>org/neo4j/driver/Driver</className>
520+
<differenceType>7012</differenceType>
521+
<method>boolean verifyAuthentication(org.neo4j.driver.AuthToken)</method>
522+
</difference>
523+
524+
<difference>
525+
<className>org/neo4j/driver/Driver</className>
526+
<differenceType>7012</differenceType>
527+
<method>boolean supportsSessionAuth()</method>
528+
</difference>
529+
530+
<difference>
531+
<className>org/neo4j/driver/AuthToken</className>
532+
<differenceType>7012</differenceType>
533+
<method>org.neo4j.driver.AuthTokenAndExpiration expiringAt(long)</method>
534+
</difference>
535+
506536
</differences>

driver/pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
<parent>
77
<groupId>org.neo4j.driver</groupId>
88
<artifactId>neo4j-java-driver-parent</artifactId>
9-
<version>5.7-SNAPSHOT</version>
9+
<version>5.8-SNAPSHOT</version>
1010
</parent>
1111

1212
<artifactId>neo4j-java-driver</artifactId>

0 commit comments

Comments
 (0)