diff --git a/community/kernel/src/test/java/org/neo4j/kernel/impl/query/Neo4jTransactionalContextTest.java b/community/kernel/src/test/java/org/neo4j/kernel/impl/query/Neo4jTransactionalContextTest.java
index 0147acface58b..c670adf4be2d5 100644
--- a/community/kernel/src/test/java/org/neo4j/kernel/impl/query/Neo4jTransactionalContextTest.java
+++ b/community/kernel/src/test/java/org/neo4j/kernel/impl/query/Neo4jTransactionalContextTest.java
@@ -1,3 +1,22 @@
+/*
+ * Copyright (c) 2002-2016 "Neo Technology,"
+ * Network Engine for Objects in Lund AB [http://neotechnology.com]
+ *
+ * This file is part of Neo4j.
+ *
+ * Neo4j is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see .
+ */
package org.neo4j.kernel.impl.query;
import org.junit.Test;
@@ -23,6 +42,7 @@
public class Neo4jTransactionalContextTest
{
+ @SuppressWarnings( "ConstantConditions" )
@Test
public void neverStopsExecutingQueryDuringCommitAndRestartTx()
{
diff --git a/community/security/src/test/java/org/neo4j/server/security/auth/AuthProceduresIT.java b/community/security/src/test/java/org/neo4j/server/security/auth/AuthProceduresIT.java
index 888d0d230c6b7..0ae0483f422d4 100644
--- a/community/security/src/test/java/org/neo4j/server/security/auth/AuthProceduresIT.java
+++ b/community/security/src/test/java/org/neo4j/server/security/auth/AuthProceduresIT.java
@@ -61,7 +61,7 @@
public class AuthProceduresIT
{
- static final String PWD_CHANGE = PASSWORD_CHANGE_REQUIRED.name().toLowerCase();
+ private static final String PWD_CHANGE = PASSWORD_CHANGE_REQUIRED.name().toLowerCase();
protected GraphDatabaseAPI db;
private EphemeralFileSystemAbstraction fs;
@@ -278,8 +278,8 @@ private void assertFail( BasicAuthSubject subject, String query, String partOfEr
containsString( partOfErrorMsg ) );
}
- void assertSuccess( BasicAuthSubject subject, String query,
- Consumer>> resultConsumer )
+ private void assertSuccess( BasicAuthSubject subject, String query,
+ Consumer>> resultConsumer )
{
assertThat(
execute( subject, query, resultConsumer ),
@@ -301,24 +301,35 @@ private String execute( BasicAuthSubject subject, String query,
}
}
- List getObjectsAsList( ResourceIterator> r, String key )
+ private List getObjectsAsList( ResourceIterator> r, String key )
{
return r.stream().map( s -> s.get( key ) ).collect( Collectors.toList() );
}
- void assertKeyIs( ResourceIterator> r, String key, String... items )
+ private void assertKeyIs( ResourceIterator> r, String key, String... items )
{
assertKeyIsArray( r, key, items );
}
- void assertKeyIsArray( ResourceIterator> r, String key, String[] items )
+ private void assertKeyIsArray( ResourceIterator> r, String key, String[] items )
{
List results = getObjectsAsList( r, key );
assertEquals( Arrays.asList( items ).size(), results.size() );
Assert.assertThat( results, containsInAnyOrder( items ) );
}
- protected void assertKeyIsMap( ResourceIterator> r, String keyKey, String valueKey, Map expected )
+ protected String[] with( String[] strs, String... moreStr )
+ {
+ return Stream.concat( Arrays.stream(strs), Arrays.stream( moreStr ) ).toArray( String[]::new );
+ }
+
+ private List listOf( String... values )
+ {
+ return Stream.of( values ).collect( Collectors.toList() );
+ }
+
+ @SuppressWarnings( "unchecked" )
+ public static void assertKeyIsMap( ResourceIterator> r, String keyKey, String valueKey, Map expected )
{
List> result = r.stream().collect( Collectors.toList() );
@@ -351,14 +362,4 @@ protected void assertKeyIsMap( ResourceIterator> r, String k
}
}
}
-
- protected String[] with( String[] strs, String... moreStr )
- {
- return Stream.concat( Arrays.stream(strs), Arrays.stream( moreStr ) ).toArray( String[]::new );
- }
-
- protected List listOf( String... values )
- {
- return Stream.of( values ).collect( Collectors.toList() );
- }
}
diff --git a/enterprise/query-logging/src/test/java/org/neo4j/kernel/impl/query/QueryLoggerIT.java b/enterprise/query-logging/src/test/java/org/neo4j/kernel/impl/query/QueryLoggerIT.java
index 4fdf877eb78a6..4e2f311110305 100644
--- a/enterprise/query-logging/src/test/java/org/neo4j/kernel/impl/query/QueryLoggerIT.java
+++ b/enterprise/query-logging/src/test/java/org/neo4j/kernel/impl/query/QueryLoggerIT.java
@@ -19,6 +19,10 @@
*/
package org.neo4j.kernel.impl.query;
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+
import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
@@ -32,19 +36,15 @@
import java.util.Map;
import java.util.concurrent.TimeUnit;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-
import org.neo4j.graphdb.GraphDatabaseService;
import org.neo4j.graphdb.ResourceIterator;
import org.neo4j.graphdb.Result;
import org.neo4j.graphdb.factory.GraphDatabaseBuilder;
import org.neo4j.graphdb.factory.GraphDatabaseSettings;
import org.neo4j.kernel.configuration.Settings;
-import org.neo4j.logging.AssertableLogProvider;
import org.neo4j.kernel.enterprise.api.security.EnterpriseAuthSubject;
-import org.neo4j.server.security.enterprise.auth.NeoShallowEmbeddedInteraction;
+import org.neo4j.logging.AssertableLogProvider;
+import org.neo4j.server.security.enterprise.auth.EmbeddedInteraction;
import org.neo4j.test.TestEnterpriseGraphDatabaseFactory;
import org.neo4j.test.rule.TestDirectory;
import org.neo4j.test.rule.fs.EphemeralFileSystemRule;
@@ -55,7 +55,6 @@
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.assertTrue;
-
import static org.neo4j.kernel.api.security.AccessMode.Static.FULL;
import static org.neo4j.kernel.impl.query.QueryEngineProvider.embeddedSession;
@@ -86,7 +85,7 @@ public void shouldLogCustomUserName() throws Throwable
// turn on query logging
databaseBuilder.setConfig( GraphDatabaseSettings.logs_directory, logsDirectory.getPath() );
databaseBuilder.setConfig( GraphDatabaseSettings.log_queries, Settings.TRUE );
- NeoShallowEmbeddedInteraction db = new NeoShallowEmbeddedInteraction( databaseBuilder );
+ EmbeddedInteraction db = new EmbeddedInteraction( databaseBuilder );
// create users
db.getManager().newUser( "mats", "neo4j", false );
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthProceduresTestLogic.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthProceduresInteractionTestBase.java
similarity index 72%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthProceduresTestLogic.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthProceduresInteractionTestBase.java
index cbad280a8e66b..314652bdf5696 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthProceduresTestLogic.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthProceduresInteractionTestBase.java
@@ -19,56 +19,37 @@
*/
package org.neo4j.server.security.enterprise.auth;
-import org.hamcrest.Matcher;
import org.junit.Rule;
import org.junit.Test;
-import java.time.OffsetDateTime;
-import java.util.Collections;
import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ExecutionException;
-import java.util.stream.Collectors;
import java.util.stream.Stream;
-import org.neo4j.bolt.v1.transport.integration.TransportTestUtil;
-import org.neo4j.bolt.v1.transport.socket.client.SocketConnection;
import org.neo4j.bolt.v1.transport.socket.client.TransportConnection;
-import org.neo4j.helpers.HostnamePort;
import org.neo4j.kernel.api.security.exception.InvalidArgumentsException;
-import org.neo4j.test.DoubleLatch;
import org.neo4j.test.rule.concurrent.ThreadingRule;
import static java.lang.String.format;
-import static java.time.format.DateTimeFormatter.ISO_OFFSET_DATE_TIME;
import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.allOf;
-import static org.hamcrest.Matchers.anyOf;
import static org.hamcrest.Matchers.contains;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.greaterThan;
-import static org.hamcrest.Matchers.greaterThanOrEqualTo;
-import static org.hamcrest.Matchers.hasEntry;
import static org.hamcrest.Matchers.hasItem;
-import static org.hamcrest.Matchers.isA;
import static org.hamcrest.Matchers.not;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
-import static org.neo4j.bolt.v1.messaging.message.InitMessage.init;
-import static org.neo4j.bolt.v1.messaging.util.MessageMatchers.msgSuccess;
-import static org.neo4j.bolt.v1.transport.integration.TransportTestUtil.eventuallyReceives;
import static org.neo4j.helpers.collection.MapUtil.map;
import static org.neo4j.kernel.api.security.AuthenticationResult.PASSWORD_CHANGE_REQUIRED;
+import static org.neo4j.server.security.auth.AuthProceduresIT.assertKeyIsMap;
import static org.neo4j.server.security.enterprise.auth.AuthProcedures.PERMISSION_DENIED;
import static org.neo4j.server.security.enterprise.auth.InternalFlatFileRealm.IS_SUSPENDED;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.ADMIN;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.ARCHITECT;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.PUBLISHER;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.READER;
-import static org.neo4j.test.matchers.CommonMatchers.itemsMatchingExactlyOneOf;
-public abstract class AuthProceduresTestLogic extends AuthTestBase
+public abstract class AuthProceduresInteractionTestBase extends ProcedureInteractionTestBase
{
private static final String PWD_CHANGE = PASSWORD_CHANGE_REQUIRED.name().toLowerCase();
@@ -129,295 +110,6 @@ public void shouldNotChangeOwnPasswordIfNewPasswordInvalid() throws Exception
"Old password and new password cannot be the same." );
}
- //---------- list running transactions -----------
-
- @Test
- public void shouldListSelfTransaction()
- {
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
- }
-
- @Test
- public void shouldNotListTransactionsIfNotAdmin()
- {
- assertFail( noneSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
- assertFail( readSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
- assertFail( writeSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
- assertFail( schemaSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
- }
-
- @Test
- public void shouldListTransactions() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 3 );
- ThreadedTransactionCreate write1 = new ThreadedTransactionCreate<>( neo, latch );
- ThreadedTransactionCreate write2 = new ThreadedTransactionCreate<>( neo, latch );
-
- String q1 = write1.execute( threading, writeSubject );
- String q2 = write2.execute( threading, writeSubject );
- latch.startAndWaitForAllToStart();
-
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions",
- map( "adminSubject", "1", "writeSubject", "2" ) ) );
-
- latch.finishAndWaitForAllToFinish();
-
- write1.closeAndAssertSuccess();
- write2.closeAndAssertSuccess();
- }
-
- @Test
- public void shouldListRestrictedTransaction()
- {
- final DoubleLatch doubleLatch = new DoubleLatch( 2 );
-
- ClassWithProcedures.setTestLatch( new ClassWithProcedures.LatchedRunnables( doubleLatch, () -> {}, () -> {} ) );
-
- new Thread( () -> assertEmpty( writeSubject, "CALL test.waitForLatch()" ) ).start();
- doubleLatch.startAndWaitForAllToStart();
- try
- {
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions",
- map( "adminSubject", "1", "writeSubject", "1" ) ) );
- }
- finally
- {
- doubleLatch.finishAndWaitForAllToFinish();
- }
- }
-
- @Test
- public void shouldListAllQueriesWhenRunningAsAdmin() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 3, true );
- String startTime = OffsetDateTime.now().format( ISO_OFFSET_DATE_TIME );
-
- ThreadedTransactionCreate read1 = new ThreadedTransactionCreate<>( neo, latch );
- ThreadedTransactionCreate read2 = new ThreadedTransactionCreate<>( neo, latch );
-
- String q1 = read1.execute( threading, readSubject, "UNWIND [1,2,3] AS x RETURN x" );
- String q2 = read2.execute( threading, readSubject, "UNWIND [4,5,6] AS y RETURN y" );
- latch.startAndWaitForAllToStart();
-
- String query = "CALL dbms.listQueries()";
- assertSuccess( adminSubject, query, r ->
- {
- Set> maps = r.stream().collect( Collectors.toSet() );
-
- Matcher> thisQuery = listedQuery( startTime, "adminSubject", query );
- Matcher> matcher1 = listedQuery( startTime, "readSubject", q1 );
- Matcher> matcher2 = listedQuery( startTime, "readSubject", q2 );
-
- assertThat( maps, itemsMatchingExactlyOneOf( matcher1, matcher2, thisQuery ) );
- } );
-
- latch.finishAndWaitForAllToFinish();
-
- read1.closeAndAssertSuccess();
- read2.closeAndAssertSuccess();
- }
-
- @Test
- public void shouldOnlyListOwnQueriesWhenNotRunningAsAdmin() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 3, true );
- String startTime = OffsetDateTime.now().format( ISO_OFFSET_DATE_TIME );
- ThreadedTransactionCreate read1 = new ThreadedTransactionCreate<>( neo, latch );
- ThreadedTransactionCreate read2 = new ThreadedTransactionCreate<>( neo, latch );
-
- String q1 = read1.execute( threading, readSubject, "UNWIND [1,2,3] AS x RETURN x" );
- String ignored = read2.execute( threading, writeSubject, "UNWIND [4,5,6] AS y RETURN y" );
- latch.startAndWaitForAllToStart();
-
- String query = "CALL dbms.listQueries()";
- assertSuccess( readSubject, query, r ->
- {
- Set> maps = r.stream().collect( Collectors.toSet() );
-
- Matcher> thisQuery = listedQuery( startTime, "readSubject", query );
- Matcher> queryMatcher = listedQuery( startTime, "readSubject", q1 );
-
- assertThat( maps, itemsMatchingExactlyOneOf( queryMatcher, thisQuery ) );
- } );
-
- latch.finishAndWaitForAllToFinish();
-
- read1.closeAndAssertSuccess();
- read2.closeAndAssertSuccess();
- }
-
-
- //---------- terminate transactions for user -----------
-
- @Test
- public void shouldTerminateTransactionForUser() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 2 );
- ThreadedTransactionCreate write = new ThreadedTransactionCreate<>( neo, latch );
- write.execute( threading, writeSubject );
- latch.startAndWaitForAllToStart();
-
- assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "writeSubject", "1" ) ) );
-
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
-
- latch.finishAndWaitForAllToFinish();
-
- write.closeAndAssertTransactionTermination();
-
- assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
- }
-
- @Test
- public void shouldTerminateOnlyGivenUsersTransaction() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 3 );
- ThreadedTransactionCreate schema = new ThreadedTransactionCreate<>( neo, latch );
- ThreadedTransactionCreate write = new ThreadedTransactionCreate<>( neo, latch );
-
- schema.execute( threading, schemaSubject );
- write.execute( threading, writeSubject );
- latch.startAndWaitForAllToStart();
-
- assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'schemaSubject' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "schemaSubject", "1" ) ) );
-
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions",
- map( "adminSubject", "1", "writeSubject", "1" ) ) );
-
- latch.finishAndWaitForAllToFinish();
-
- schema.closeAndAssertTransactionTermination();
- write.closeAndAssertSuccess();
-
- assertSuccess( adminSubject, "MATCH (n:Test) RETURN n.name AS name",
- r -> assertKeyIs( r, "name", "writeSubject-node" ) );
- }
-
- @Test
- public void shouldTerminateAllTransactionsForGivenUser() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 3 );
- ThreadedTransactionCreate schema1 = new ThreadedTransactionCreate<>( neo, latch );
- ThreadedTransactionCreate schema2 = new ThreadedTransactionCreate<>( neo, latch );
-
- schema1.execute( threading, schemaSubject );
- schema2.execute( threading, schemaSubject );
- latch.startAndWaitForAllToStart();
-
- assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'schemaSubject' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "schemaSubject", "2" ) ) );
-
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
-
- latch.finishAndWaitForAllToFinish();
-
- schema1.closeAndAssertTransactionTermination();
- schema2.closeAndAssertTransactionTermination();
-
- assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
- }
-
- @Test
- public void shouldNotTerminateTerminationTransaction() throws InterruptedException, ExecutionException
- {
- assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'adminSubject' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "adminSubject", "0" ) ) );
- assertSuccess( readSubject, "CALL dbms.security.terminateTransactionsForUser( 'readSubject' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "readSubject", "0" ) ) );
- }
-
- @Test
- public void shouldTerminateSelfTransactionsExceptTerminationTransactionIfAdmin() throws Throwable
- {
- shouldTerminateSelfTransactionsExceptTerminationTransaction( adminSubject );
- }
-
- @Test
- public void shouldTerminateSelfTransactionsExceptTerminationTransactionIfNotAdmin() throws Throwable
- {
- shouldTerminateSelfTransactionsExceptTerminationTransaction( writeSubject );
- }
-
- private void shouldTerminateSelfTransactionsExceptTerminationTransaction( S subject ) throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 2 );
- ThreadedTransactionCreate create = new ThreadedTransactionCreate<>( neo, latch );
- create.execute( threading, subject );
-
- latch.startAndWaitForAllToStart();
-
- String subjectName = neo.nameOf( subject );
- assertSuccess( subject, "CALL dbms.security.terminateTransactionsForUser( '" + subjectName + "' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( subjectName, "1" ) ) );
-
- latch.finishAndWaitForAllToFinish();
-
- create.closeAndAssertTransactionTermination();
-
- assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
- }
-
- @Test
- public void shouldNotTerminateTransactionsIfNonExistentUser() throws InterruptedException, ExecutionException
- {
- assertFail( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'Petra' )", "User 'Petra' does not exist" );
- assertFail( adminSubject, "CALL dbms.security.terminateTransactionsForUser( '' )", "User '' does not exist" );
- }
-
- @Test
- public void shouldNotTerminateTransactionsIfNotAdmin() throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 2 );
- ThreadedTransactionCreate write = new ThreadedTransactionCreate<>( neo, latch );
- write.execute( threading, writeSubject );
- latch.startAndWaitForAllToStart();
-
- assertFail( noneSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", PERMISSION_DENIED );
- assertFail( pwdSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", CHANGE_PWD_ERR_MSG );
- assertFail( readSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", PERMISSION_DENIED );
- assertFail( schemaSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", PERMISSION_DENIED );
-
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIs( r, "username", "adminSubject", "writeSubject" ) );
-
- latch.finishAndWaitForAllToFinish();
-
- write.closeAndAssertSuccess();
-
- assertSuccess( adminSubject, "MATCH (n:Test) RETURN n.name AS name",
- r -> assertKeyIs( r, "name", "writeSubject-node" ) );
- }
-
- @Test
- public void shouldTerminateRestrictedTransaction()
- {
- final DoubleLatch doubleLatch = new DoubleLatch( 2 );
-
- ClassWithProcedures.setTestLatch( new ClassWithProcedures.LatchedRunnables( doubleLatch, () -> {}, () -> {} ) );
-
- new Thread( () -> assertFail( writeSubject, "CALL test.waitForLatch()", "Explicitly terminated by the user." ) )
- .start();
-
- doubleLatch.startAndWaitForAllToStart();
- try
- {
- assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )",
- r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "writeSubject", "1" ) ) );
- }
- finally
- {
- doubleLatch.finishAndWaitForAllToFinish();
- }
- }
-
//---------- change user password -----------
// Should change password for admin subject and valid user
@@ -1288,79 +980,9 @@ public void shouldSetCorrectMultiRolePermissions() throws Exception
assertEmpty( schemaSubject, "CALL dbms.security.changePassword( '321' )" );
}
- // --------------------- helpers -----------------------
-
- private void shouldTerminateTransactionsForUser( S subject, String procedure ) throws Throwable
- {
- DoubleLatch latch = new DoubleLatch( 2 );
- ThreadedTransactionCreate userThread = new ThreadedTransactionCreate<>( neo, latch );
- userThread.execute( threading, subject );
- latch.startAndWaitForAllToStart();
-
- assertEmpty( adminSubject, "CALL " + format(procedure, neo.nameOf( subject ) ) );
-
- assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
- r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
-
- latch.finishAndWaitForAllToFinish();
-
- userThread.closeAndAssertTransactionTermination();
-
- assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
- }
-
- private TransportConnection startBoltSession( String username, String password ) throws Exception
- {
- TransportConnection connection = new SocketConnection();
- HostnamePort address = new HostnamePort( "localhost:7687" );
- Map authToken = map( "principal", username, "credentials", password, "scheme", "basic" );
-
- connection.connect( address ).send( TransportTestUtil.acceptedVersions( 1, 0, 0, 0 ) )
- .send( TransportTestUtil.chunk( init( "TestClient/1.1", authToken ) ) );
-
- assertThat( connection, eventuallyReceives( new byte[]{0, 0, 0, 1} ) );
- assertThat( connection, eventuallyReceives( msgSuccess() ) );
- return connection;
- }
-
- //---------- matchers-----------
- private Matcher> listedQuery( String startTime, String username, String query )
- {
- return allOf(
- hasQuery( query ),
- hasUsername( username ),
- hasQueryId(),
- hasStartTimeAfter( startTime ),
- hasNoParameters()
- );
- }
- @SuppressWarnings( "unchecked" )
- private Matcher> hasQuery( String query )
- {
- return (Matcher>) (Matcher) hasEntry( equalTo( "query" ), equalTo( query ) );
- }
-
- @SuppressWarnings( "unchecked" )
- private Matcher> hasUsername( String username )
- {
- return (Matcher>) (Matcher) hasEntry( equalTo( "username" ), equalTo( username ) );
- }
-
- @SuppressWarnings( "unchecked" )
- private Matcher> hasQueryId()
- {
- return (Matcher>) (Matcher) hasEntry( equalTo( "queryId" ), anyOf( (Matcher) isA( Integer.class ), isA( Long.class ) ) );
- }
-
- @SuppressWarnings( "unchecked" )
- private Matcher> hasStartTimeAfter( String base )
- {
- return (Matcher>) (Matcher) hasEntry( equalTo( "startTime" ), allOf( greaterThanOrEqualTo( base ) ) );
- }
-
- @SuppressWarnings( "unchecked" )
- private Matcher> hasNoParameters()
+ @Override
+ protected ThreadingRule threading()
{
- return (Matcher>) (Matcher) hasEntry( equalTo( "parameters" ), equalTo ( Collections.emptyMap() ) );
+ return threading;
}
-}
\ No newline at end of file
+}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthScenariosLogic.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthScenariosInteractionTestBase.java
similarity index 99%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthScenariosLogic.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthScenariosInteractionTestBase.java
index be990f5e50e56..dde761b2b8555 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthScenariosLogic.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthScenariosInteractionTestBase.java
@@ -22,7 +22,6 @@
import org.junit.Rule;
import org.junit.Test;
-
import org.neo4j.graphdb.Transaction;
import org.neo4j.kernel.api.Statement;
import org.neo4j.kernel.impl.core.ThreadToStatementContextBridge;
@@ -32,15 +31,14 @@
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.greaterThan;
import static org.hamcrest.Matchers.lessThan;
-
import static org.junit.Assert.fail;
-import static org.neo4j.server.security.enterprise.auth.AuthProcedures.*;
+import static org.neo4j.server.security.enterprise.auth.AuthProcedures.PERMISSION_DENIED;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.ADMIN;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.ARCHITECT;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.PUBLISHER;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.READER;
-public abstract class AuthScenariosLogic extends AuthTestBase
+public abstract class AuthScenariosInteractionTestBase extends ProcedureInteractionTestBase
{
@Rule
public final ThreadingRule threading = new ThreadingRule();
@@ -767,4 +765,10 @@ public void changeUserPassword3() throws Throwable
testSuccessfulRead( subject, 3 );
assertFail( subject, "CALL dbms.security.changeUserPassword('Craig', '123')", PERMISSION_DENIED );
}
+
+ @Override
+ protected ThreadingRule threading()
+ {
+ return threading;
+ }
}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltProceduresIT.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltAuthProceduresInteractionTest.java
similarity index 84%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltProceduresIT.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltAuthProceduresInteractionTest.java
index a4037e543f653..423b8febad16c 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltProceduresIT.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltAuthProceduresInteractionTest.java
@@ -28,24 +28,22 @@
import org.neo4j.test.TestGraphDatabaseFactory;
import org.neo4j.test.rule.SuppressOutput;
-public class BoltProceduresIT extends AuthProceduresTestLogic
+public class BoltAuthProceduresInteractionTest extends AuthProceduresInteractionTestBase
{
private Neo4jWithSocket server = new Neo4jWithSocket( getTestGraphDatabaseFactory(),
- settings -> {
- settings.put( GraphDatabaseSettings.auth_enabled, "true" );
- } );
+ settings -> settings.put( GraphDatabaseSettings.auth_enabled, "true" ) );
@Rule
public final RuleChain ruleChain = RuleChain.outerRule( SuppressOutput.suppressAll() ).around( server );
- public BoltProceduresIT()
+ public BoltAuthProceduresInteractionTest()
{
super();
IS_EMBEDDED = false;
IS_BOLT = true;
}
- protected TestGraphDatabaseFactory getTestGraphDatabaseFactory()
+ private TestGraphDatabaseFactory getTestGraphDatabaseFactory()
{
return new TestEnterpriseGraphDatabaseFactory();
}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltScenariosIT.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltAuthScenariosInteractionTest.java
similarity index 84%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltScenariosIT.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltAuthScenariosInteractionTest.java
index 1b637c252078e..8135e23928dd6 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltScenariosIT.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltAuthScenariosInteractionTest.java
@@ -28,24 +28,22 @@
import org.neo4j.test.TestGraphDatabaseFactory;
import org.neo4j.test.rule.SuppressOutput;
-public class BoltScenariosIT extends AuthScenariosLogic
+public class BoltAuthScenariosInteractionTest extends AuthScenariosInteractionTestBase
{
private Neo4jWithSocket server = new Neo4jWithSocket( getTestGraphDatabaseFactory(),
- settings -> {
- settings.put( GraphDatabaseSettings.auth_enabled, "true" );
- } );
+ settings -> settings.put( GraphDatabaseSettings.auth_enabled, "true" ) );
@Rule
public final RuleChain ruleChain = RuleChain.outerRule( SuppressOutput.suppressAll() ).around( server );
- public BoltScenariosIT()
+ public BoltAuthScenariosInteractionTest()
{
super();
IS_EMBEDDED = false;
IS_BOLT = true;
}
- protected TestGraphDatabaseFactory getTestGraphDatabaseFactory()
+ private TestGraphDatabaseFactory getTestGraphDatabaseFactory()
{
return new TestEnterpriseGraphDatabaseFactory();
}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltBuiltInProceduresInteractionTest.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltBuiltInProceduresInteractionTest.java
new file mode 100644
index 0000000000000..2b7d2ba8c36c0
--- /dev/null
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BoltBuiltInProceduresInteractionTest.java
@@ -0,0 +1,56 @@
+/*
+ * Copyright (c) 2002-2016 "Neo Technology,"
+ * Network Engine for Objects in Lund AB [http://neotechnology.com]
+ *
+ * This file is part of Neo4j.
+ *
+ * Neo4j is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+package org.neo4j.server.security.enterprise.auth;
+
+import org.junit.Rule;
+import org.junit.rules.RuleChain;
+
+import org.neo4j.bolt.v1.transport.integration.Neo4jWithSocket;
+import org.neo4j.graphdb.factory.GraphDatabaseSettings;
+import org.neo4j.test.TestEnterpriseGraphDatabaseFactory;
+import org.neo4j.test.TestGraphDatabaseFactory;
+import org.neo4j.test.rule.SuppressOutput;
+
+public class BoltBuiltInProceduresInteractionTest extends BuiltInProceduresInteractionTestBase
+{
+ private Neo4jWithSocket server = new Neo4jWithSocket( getTestGraphDatabaseFactory(),
+ settings -> settings.put( GraphDatabaseSettings.auth_enabled, "true" ) );
+
+ @Rule
+ public final RuleChain ruleChain = RuleChain.outerRule( SuppressOutput.suppressAll() ).around( server );
+
+ public BoltBuiltInProceduresInteractionTest()
+ {
+ super();
+ IS_EMBEDDED = false;
+ IS_BOLT = true;
+ }
+
+ private TestGraphDatabaseFactory getTestGraphDatabaseFactory()
+ {
+ return new TestEnterpriseGraphDatabaseFactory();
+ }
+
+ @Override
+ public NeoInteractionLevel setUpNeoServer() throws Throwable
+ {
+ return new BoltInteraction( server );
+ }
+}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BuiltInProceduresInteractionTestBase.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BuiltInProceduresInteractionTestBase.java
new file mode 100644
index 0000000000000..296241cba536a
--- /dev/null
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/BuiltInProceduresInteractionTestBase.java
@@ -0,0 +1,394 @@
+/*
+ * Copyright (c) 2002-2016 "Neo Technology,"
+ * Network Engine for Objects in Lund AB [http://neotechnology.com]
+ *
+ * This file is part of Neo4j.
+ *
+ * Neo4j is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+package org.neo4j.server.security.enterprise.auth;
+
+import org.hamcrest.Matcher;
+import org.junit.Rule;
+import org.junit.Test;
+
+import java.time.OffsetDateTime;
+import java.util.Collections;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ExecutionException;
+import java.util.stream.Collectors;
+
+import org.neo4j.test.DoubleLatch;
+import org.neo4j.test.rule.concurrent.ThreadingRule;
+
+import static java.time.format.DateTimeFormatter.ISO_OFFSET_DATE_TIME;
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.allOf;
+import static org.hamcrest.Matchers.anyOf;
+import static org.hamcrest.Matchers.equalTo;
+import static org.hamcrest.Matchers.greaterThanOrEqualTo;
+import static org.hamcrest.Matchers.hasEntry;
+import static org.hamcrest.Matchers.isA;
+import static org.neo4j.helpers.collection.MapUtil.map;
+import static org.neo4j.kernel.api.security.AuthenticationResult.PASSWORD_CHANGE_REQUIRED;
+import static org.neo4j.server.security.auth.AuthProceduresIT.assertKeyIsMap;
+import static org.neo4j.server.security.enterprise.auth.AuthProcedures.PERMISSION_DENIED;
+import static org.neo4j.test.matchers.CommonMatchers.itemsMatchingExactlyOneOf;
+
+public abstract class BuiltInProceduresInteractionTestBase extends ProcedureInteractionTestBase
+{
+ private static final String PWD_CHANGE = PASSWORD_CHANGE_REQUIRED.name().toLowerCase();
+
+ @Rule
+ public final ThreadingRule threading = new ThreadingRule();
+
+ //---------- list running transactions -----------
+
+ @Test
+ public void shouldListSelfTransaction()
+ {
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
+ }
+
+ @Test
+ public void shouldNotListTransactionsIfNotAdmin()
+ {
+ assertFail( noneSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
+ assertFail( readSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
+ assertFail( writeSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
+ assertFail( schemaSubject, "CALL dbms.security.listTransactions()", PERMISSION_DENIED );
+ }
+
+ @Test
+ public void shouldListTransactions() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 3 );
+ ThreadedTransactionCreate write1 = new ThreadedTransactionCreate<>( neo, latch );
+ ThreadedTransactionCreate write2 = new ThreadedTransactionCreate<>( neo, latch );
+
+ String q1 = write1.execute( threading, writeSubject );
+ String q2 = write2.execute( threading, writeSubject );
+ latch.startAndWaitForAllToStart();
+
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions",
+ map( "adminSubject", "1", "writeSubject", "2" ) ) );
+
+ latch.finishAndWaitForAllToFinish();
+
+ write1.closeAndAssertSuccess();
+ write2.closeAndAssertSuccess();
+ }
+
+ @Test
+ public void shouldListRestrictedTransaction()
+ {
+ final DoubleLatch doubleLatch = new DoubleLatch( 2 );
+
+ ClassWithProcedures.setTestLatch( new ClassWithProcedures.LatchedRunnables( doubleLatch, () -> {}, () -> {} ) );
+
+ new Thread( () -> assertEmpty( writeSubject, "CALL test.waitForLatch()" ) ).start();
+ doubleLatch.startAndWaitForAllToStart();
+ try
+ {
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions",
+ map( "adminSubject", "1", "writeSubject", "1" ) ) );
+ }
+ finally
+ {
+ doubleLatch.finishAndWaitForAllToFinish();
+ }
+ }
+
+ @SuppressWarnings( "unchecked" )
+ @Test
+ public void shouldListAllQueriesWhenRunningAsAdmin() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 3, true );
+ String startTime = OffsetDateTime.now().format( ISO_OFFSET_DATE_TIME );
+
+ ThreadedTransactionCreate read1 = new ThreadedTransactionCreate<>( neo, latch );
+ ThreadedTransactionCreate read2 = new ThreadedTransactionCreate<>( neo, latch );
+
+ String q1 = read1.execute( threading, readSubject, "UNWIND [1,2,3] AS x RETURN x" );
+ String q2 = read2.execute( threading, readSubject, "UNWIND [4,5,6] AS y RETURN y" );
+ latch.startAndWaitForAllToStart();
+
+ String query = "CALL dbms.listQueries()";
+ assertSuccess( adminSubject, query, r ->
+ {
+ Set> maps = r.stream().collect( Collectors.toSet() );
+
+ Matcher> thisQuery = listedQuery( startTime, "adminSubject", query );
+ Matcher> matcher1 = listedQuery( startTime, "readSubject", q1 );
+ Matcher> matcher2 = listedQuery( startTime, "readSubject", q2 );
+
+ assertThat( maps, itemsMatchingExactlyOneOf( matcher1, matcher2, thisQuery ) );
+ } );
+
+ latch.finishAndWaitForAllToFinish();
+
+ read1.closeAndAssertSuccess();
+ read2.closeAndAssertSuccess();
+ }
+
+ @Test
+ public void shouldOnlyListOwnQueriesWhenNotRunningAsAdmin() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 3, true );
+ String startTime = OffsetDateTime.now().format( ISO_OFFSET_DATE_TIME );
+ ThreadedTransactionCreate read1 = new ThreadedTransactionCreate<>( neo, latch );
+ ThreadedTransactionCreate read2 = new ThreadedTransactionCreate<>( neo, latch );
+
+ String q1 = read1.execute( threading, readSubject, "UNWIND [1,2,3] AS x RETURN x" );
+ String ignored = read2.execute( threading, writeSubject, "UNWIND [4,5,6] AS y RETURN y" );
+ latch.startAndWaitForAllToStart();
+
+ String query = "CALL dbms.listQueries()";
+ assertSuccess( readSubject, query, r ->
+ {
+ Set> maps = r.stream().collect( Collectors.toSet() );
+
+ Matcher> thisQuery = listedQuery( startTime, "readSubject", query );
+ Matcher> queryMatcher = listedQuery( startTime, "readSubject", q1 );
+
+ assertThat( maps, itemsMatchingExactlyOneOf( queryMatcher, thisQuery ) );
+ } );
+
+ latch.finishAndWaitForAllToFinish();
+
+ read1.closeAndAssertSuccess();
+ read2.closeAndAssertSuccess();
+ }
+
+
+ //---------- terminate transactions for user -----------
+
+ @Test
+ public void shouldTerminateTransactionForUser() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 2 );
+ ThreadedTransactionCreate write = new ThreadedTransactionCreate<>( neo, latch );
+ write.execute( threading, writeSubject );
+ latch.startAndWaitForAllToStart();
+
+ assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "writeSubject", "1" ) ) );
+
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
+
+ latch.finishAndWaitForAllToFinish();
+
+ write.closeAndAssertTransactionTermination();
+
+ assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
+ }
+
+ @Test
+ public void shouldTerminateOnlyGivenUsersTransaction() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 3 );
+ ThreadedTransactionCreate schema = new ThreadedTransactionCreate<>( neo, latch );
+ ThreadedTransactionCreate write = new ThreadedTransactionCreate<>( neo, latch );
+
+ schema.execute( threading, schemaSubject );
+ write.execute( threading, writeSubject );
+ latch.startAndWaitForAllToStart();
+
+ assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'schemaSubject' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "schemaSubject", "1" ) ) );
+
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions",
+ map( "adminSubject", "1", "writeSubject", "1" ) ) );
+
+ latch.finishAndWaitForAllToFinish();
+
+ schema.closeAndAssertTransactionTermination();
+ write.closeAndAssertSuccess();
+
+ assertSuccess( adminSubject, "MATCH (n:Test) RETURN n.name AS name",
+ r -> assertKeyIs( r, "name", "writeSubject-node" ) );
+ }
+
+ @Test
+ public void shouldTerminateAllTransactionsForGivenUser() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 3 );
+ ThreadedTransactionCreate schema1 = new ThreadedTransactionCreate<>( neo, latch );
+ ThreadedTransactionCreate schema2 = new ThreadedTransactionCreate<>( neo, latch );
+
+ schema1.execute( threading, schemaSubject );
+ schema2.execute( threading, schemaSubject );
+ latch.startAndWaitForAllToStart();
+
+ assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'schemaSubject' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "schemaSubject", "2" ) ) );
+
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
+
+ latch.finishAndWaitForAllToFinish();
+
+ schema1.closeAndAssertTransactionTermination();
+ schema2.closeAndAssertTransactionTermination();
+
+ assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
+ }
+
+ @Test
+ public void shouldNotTerminateTerminationTransaction() throws InterruptedException, ExecutionException
+ {
+ assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'adminSubject' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "adminSubject", "0" ) ) );
+ assertSuccess( readSubject, "CALL dbms.security.terminateTransactionsForUser( 'readSubject' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "readSubject", "0" ) ) );
+ }
+
+ @Test
+ public void shouldTerminateSelfTransactionsExceptTerminationTransactionIfAdmin() throws Throwable
+ {
+ shouldTerminateSelfTransactionsExceptTerminationTransaction( adminSubject );
+ }
+
+ @Test
+ public void shouldTerminateSelfTransactionsExceptTerminationTransactionIfNotAdmin() throws Throwable
+ {
+ shouldTerminateSelfTransactionsExceptTerminationTransaction( writeSubject );
+ }
+
+ private void shouldTerminateSelfTransactionsExceptTerminationTransaction( S subject ) throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 2 );
+ ThreadedTransactionCreate create = new ThreadedTransactionCreate<>( neo, latch );
+ create.execute( threading, subject );
+
+ latch.startAndWaitForAllToStart();
+
+ String subjectName = neo.nameOf( subject );
+ assertSuccess( subject, "CALL dbms.security.terminateTransactionsForUser( '" + subjectName + "' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( subjectName, "1" ) ) );
+
+ latch.finishAndWaitForAllToFinish();
+
+ create.closeAndAssertTransactionTermination();
+
+ assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
+ }
+
+ @Test
+ public void shouldNotTerminateTransactionsIfNonExistentUser() throws InterruptedException, ExecutionException
+ {
+ assertFail( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'Petra' )", "User 'Petra' does not exist" );
+ assertFail( adminSubject, "CALL dbms.security.terminateTransactionsForUser( '' )", "User '' does not exist" );
+ }
+
+ @Test
+ public void shouldNotTerminateTransactionsIfNotAdmin() throws Throwable
+ {
+ DoubleLatch latch = new DoubleLatch( 2 );
+ ThreadedTransactionCreate write = new ThreadedTransactionCreate<>( neo, latch );
+ write.execute( threading, writeSubject );
+ latch.startAndWaitForAllToStart();
+
+ assertFail( noneSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", PERMISSION_DENIED );
+ assertFail( pwdSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", CHANGE_PWD_ERR_MSG );
+ assertFail( readSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", PERMISSION_DENIED );
+ assertFail( schemaSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )", PERMISSION_DENIED );
+
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIs( r, "username", "adminSubject", "writeSubject" ) );
+
+ latch.finishAndWaitForAllToFinish();
+
+ write.closeAndAssertSuccess();
+
+ assertSuccess( adminSubject, "MATCH (n:Test) RETURN n.name AS name",
+ r -> assertKeyIs( r, "name", "writeSubject-node" ) );
+ }
+
+ @Test
+ public void shouldTerminateRestrictedTransaction()
+ {
+ final DoubleLatch doubleLatch = new DoubleLatch( 2 );
+
+ ClassWithProcedures.setTestLatch( new ClassWithProcedures.LatchedRunnables( doubleLatch, () -> {}, () -> {} ) );
+
+ new Thread( () -> assertFail( writeSubject, "CALL test.waitForLatch()", "Explicitly terminated by the user." ) )
+ .start();
+
+ doubleLatch.startAndWaitForAllToStart();
+ try
+ {
+ assertSuccess( adminSubject, "CALL dbms.security.terminateTransactionsForUser( 'writeSubject' )",
+ r -> assertKeyIsMap( r, "username", "transactionsTerminated", map( "writeSubject", "1" ) ) );
+ }
+ finally
+ {
+ doubleLatch.finishAndWaitForAllToFinish();
+ }
+ }
+
+ //---------- matchers-----------
+
+ private Matcher> listedQuery( String startTime, String username, String query )
+ {
+ return allOf(
+ hasQuery( query ),
+ hasUsername( username ),
+ hasQueryId(),
+ hasStartTimeAfter( startTime ),
+ hasNoParameters()
+ );
+ }
+ @SuppressWarnings( "unchecked" )
+ private Matcher> hasQuery( String query )
+ {
+ return (Matcher>) (Matcher) hasEntry( equalTo( "query" ), equalTo( query ) );
+ }
+
+ @SuppressWarnings( "unchecked" )
+ private Matcher> hasUsername( String username )
+ {
+ return (Matcher>) (Matcher) hasEntry( equalTo( "username" ), equalTo( username ) );
+ }
+
+ @SuppressWarnings( "unchecked" )
+ private Matcher> hasQueryId()
+ {
+ return (Matcher>) (Matcher) hasEntry( equalTo( "queryId" ), anyOf( (Matcher) isA( Integer.class ), isA( Long.class ) ) );
+ }
+
+ @SuppressWarnings( "unchecked" )
+ private Matcher> hasStartTimeAfter( String base )
+ {
+ return (Matcher>) (Matcher) hasEntry( equalTo( "startTime" ), allOf( greaterThanOrEqualTo( base ) ) );
+ }
+
+ @SuppressWarnings( "unchecked" )
+ private Matcher> hasNoParameters()
+ {
+ return (Matcher>) (Matcher) hasEntry( equalTo( "parameters" ), equalTo ( Collections.emptyMap() ) );
+ }
+
+ @Override
+ protected ThreadingRule threading()
+ {
+ return threading;
+ }
+}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedAuthProceduresInteractionTest.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedAuthProceduresInteractionTest.java
new file mode 100644
index 0000000000000..d64875885b122
--- /dev/null
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedAuthProceduresInteractionTest.java
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2002-2016 "Neo Technology,"
+ * Network Engine for Objects in Lund AB [http://neotechnology.com]
+ *
+ * This file is part of Neo4j.
+ *
+ * Neo4j is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+package org.neo4j.server.security.enterprise.auth;
+
+import org.neo4j.kernel.enterprise.api.security.EnterpriseAuthSubject;
+
+public class EmbeddedAuthProceduresInteractionTest extends AuthProceduresInteractionTestBase
+{
+ @Override
+ protected NeoInteractionLevel setUpNeoServer() throws Throwable
+ {
+ return new EmbeddedInteraction();
+ }
+}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedScenariosTest.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedAuthScenariosInteractionTest.java
similarity index 87%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedScenariosTest.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedAuthScenariosInteractionTest.java
index 1a3c036231939..0dde2d02dfaf5 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedScenariosTest.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedAuthScenariosInteractionTest.java
@@ -21,11 +21,11 @@
import org.neo4j.kernel.enterprise.api.security.EnterpriseAuthSubject;
-public class NeoShallowEmbeddedScenariosTest extends AuthScenariosLogic
+public class EmbeddedAuthScenariosInteractionTest extends AuthScenariosInteractionTestBase
{
@Override
protected NeoInteractionLevel setUpNeoServer() throws Throwable
{
- return new NeoShallowEmbeddedInteraction();
+ return new EmbeddedInteraction();
}
}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedProceduresTest.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedBuiltInProceduresTest.java
similarity index 87%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedProceduresTest.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedBuiltInProceduresTest.java
index 1a0e92d5ed8db..aecb88b36e125 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedProceduresTest.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedBuiltInProceduresTest.java
@@ -21,11 +21,11 @@
import org.neo4j.kernel.enterprise.api.security.EnterpriseAuthSubject;
-public class NeoShallowEmbeddedProceduresTest extends AuthProceduresTestLogic
+public class EmbeddedBuiltInProceduresTest extends BuiltInProceduresInteractionTestBase
{
@Override
protected NeoInteractionLevel setUpNeoServer() throws Throwable
{
- return new NeoShallowEmbeddedInteraction();
+ return new EmbeddedInteraction();
}
}
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedInteraction.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedInteraction.java
similarity index 95%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedInteraction.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedInteraction.java
index 7c1b885afe548..79761a0fa2323 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/NeoShallowEmbeddedInteraction.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/EmbeddedInteraction.java
@@ -40,18 +40,18 @@
import static org.neo4j.graphdb.factory.GraphDatabaseSettings.boltConnector;
import static org.neo4j.server.security.auth.SecurityTestUtils.authToken;
-public class NeoShallowEmbeddedInteraction implements NeoInteractionLevel
+public class EmbeddedInteraction implements NeoInteractionLevel
{
private GraphDatabaseFacade db;
private MultiRealmAuthManager manager;
private EnterpriseUserManager userManager;
- NeoShallowEmbeddedInteraction() throws Throwable
+ EmbeddedInteraction() throws Throwable
{
this(new TestEnterpriseGraphDatabaseFactory().newImpermanentDatabaseBuilder());
}
- public NeoShallowEmbeddedInteraction( GraphDatabaseBuilder builder ) throws Throwable
+ public EmbeddedInteraction( GraphDatabaseBuilder builder ) throws Throwable
{
builder.setConfig( boltConnector( "0" ).enabled, "true" );
builder.setConfig( boltConnector( "0" ).encryption_level, OPTIONAL.name() );
diff --git a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthTestBase.java b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/ProcedureInteractionTestBase.java
similarity index 83%
rename from enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthTestBase.java
rename to enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/ProcedureInteractionTestBase.java
index 35663c4be5946..58625778d5bba 100644
--- a/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/AuthTestBase.java
+++ b/enterprise/security/src/test/java/org/neo4j/server/security/enterprise/auth/ProcedureInteractionTestBase.java
@@ -31,18 +31,22 @@
import java.util.stream.Stream;
import org.neo4j.bolt.v1.transport.integration.Neo4jWithSocket;
+import org.neo4j.bolt.v1.transport.integration.TransportTestUtil;
+import org.neo4j.bolt.v1.transport.socket.client.SocketConnection;
+import org.neo4j.bolt.v1.transport.socket.client.TransportConnection;
import org.neo4j.graphdb.GraphDatabaseService;
import org.neo4j.graphdb.ResourceIterator;
-import org.neo4j.graphdb.Result;
+import org.neo4j.helpers.HostnamePort;
import org.neo4j.kernel.api.security.exception.InvalidArgumentsException;
import org.neo4j.kernel.impl.proc.Procedures;
import org.neo4j.logging.Log;
import org.neo4j.procedure.Context;
import org.neo4j.procedure.Procedure;
import org.neo4j.test.DoubleLatch;
+import org.neo4j.test.rule.concurrent.ThreadingRule;
+import static java.lang.String.format;
import static java.util.stream.Collectors.toList;
-
import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.either;
import static org.hamcrest.MatcherAssert.assertThat;
@@ -51,33 +55,37 @@
import static org.hamcrest.Matchers.not;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
+import static org.neo4j.bolt.v1.messaging.message.InitMessage.init;
+import static org.neo4j.bolt.v1.messaging.util.MessageMatchers.msgSuccess;
+import static org.neo4j.bolt.v1.transport.integration.TransportTestUtil.eventuallyReceives;
+import static org.neo4j.helpers.collection.MapUtil.map;
import static org.neo4j.procedure.Procedure.Mode.READ;
import static org.neo4j.procedure.Procedure.Mode.WRITE;
+import static org.neo4j.server.security.auth.AuthProceduresIT.assertKeyIsMap;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.ADMIN;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.ARCHITECT;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.PUBLISHER;
import static org.neo4j.server.security.enterprise.auth.PredefinedRolesBuilder.READER;
-abstract class AuthTestBase
+abstract class ProcedureInteractionTestBase
{
protected boolean PWD_CHANGE_CHECK_FIRST = false;
protected String CHANGE_PWD_ERR_MSG = AuthProcedures.PERMISSION_DENIED;
- protected String BOLT_PWD_ERR_MSG =
+ private String BOLT_PWD_ERR_MSG =
"The credentials you provided were valid, but must be changed before you can use this instance.";
- protected String READ_OPS_NOT_ALLOWED = "Read operations are not allowed";
- protected String WRITE_OPS_NOT_ALLOWED = "Write operations are not allowed";
- protected String SCHEMA_OPS_NOT_ALLOWED = "Schema operations are not allowed";
+ String READ_OPS_NOT_ALLOWED = "Read operations are not allowed";
+ String WRITE_OPS_NOT_ALLOWED = "Write operations are not allowed";
+ String SCHEMA_OPS_NOT_ALLOWED = "Schema operations are not allowed";
protected boolean IS_EMBEDDED = true;
- protected boolean IS_BOLT = false;
+ boolean IS_BOLT = false;
- protected String pwdReqErrMsg( String errMsg )
+ String pwdReqErrMsg( String errMsg )
{
return PWD_CHANGE_CHECK_FIRST ? CHANGE_PWD_ERR_MSG : IS_EMBEDDED ? errMsg : BOLT_PWD_ERR_MSG;
}
- final String EMPTY_ROLE = "empty";
+ private final String EMPTY_ROLE = "empty";
S adminSubject;
S schemaSubject;
@@ -90,7 +98,9 @@ protected String pwdReqErrMsg( String errMsg )
"writeSubject", "pwdSubject", "noneSubject", "neo4j" };
String[] initialRoles = { ADMIN, ARCHITECT, PUBLISHER, READER, EMPTY_ROLE };
- protected EnterpriseUserManager userManager;
+ protected abstract ThreadingRule threading();
+
+ EnterpriseUserManager userManager;
protected NeoInteractionLevel neo;
@@ -138,7 +148,7 @@ protected String[] with( String[] strs, String... moreStr )
return Stream.concat( Arrays.stream(strs), Arrays.stream( moreStr ) ).toArray( String[]::new );
}
- protected List listOf( String... values )
+ List listOf( String... values )
{
return Stream.of( values ).collect( toList() );
}
@@ -321,7 +331,7 @@ void assertFail( S subject, String call, String partOfErrorMsg )
assertThat( err, containsString( partOfErrorMsg ) );
}
- void assertFail( S subject, String call, String partOfErrorMsg1, String partOfErrorMsg2 )
+ private void assertFail( S subject, String call, String partOfErrorMsg1, String partOfErrorMsg2 )
{
String err = assertCallEmpty( subject, call );
assertThat( err, not( equalTo( "" ) ) );
@@ -367,48 +377,50 @@ void assertKeyIs( ResourceIterator> r, String key, String...
assertKeyIsArray( r, key, items );
}
- void assertKeyIsArray( ResourceIterator> r, String key, String[] items )
+ private void assertKeyIsArray( ResourceIterator> r, String key, String[] items )
{
List results = getObjectsAsList( r, key );
assertEquals( Arrays.asList( items ).size(), results.size() );
Assert.assertThat( results, containsInAnyOrder( items ) );
}
- protected void assertKeyIsMap( ResourceIterator> r, String keyKey, String valueKey, Map expected )
+ // --------------------- helpers -----------------------
+
+ void shouldTerminateTransactionsForUser( S subject, String procedure ) throws Throwable
{
- List> result = r.stream().collect( toList() );
+ DoubleLatch latch = new DoubleLatch( 2 );
+ ThreadedTransactionCreate userThread = new ThreadedTransactionCreate<>( neo, latch );
+ userThread.execute( threading(), subject );
+ latch.startAndWaitForAllToStart();
- assertEquals( "Results for should have size " + expected.size() + " but was " + result.size(),
- expected.size(), result.size() );
+ assertEmpty( adminSubject, "CALL " + format(procedure, neo.nameOf( subject ) ) );
- for ( Map row : result )
- {
- String key = (String) row.get( keyKey );
- assertTrue( "Unexpected key '" + key + "'", expected.containsKey( key ) );
+ assertSuccess( adminSubject, "CALL dbms.security.listTransactions()",
+ r -> assertKeyIsMap( r, "username", "activeTransactions", map( "adminSubject", "1" ) ) );
- assertTrue( "Value key '" + valueKey + "' not found in results", row.containsKey( valueKey ) );
- Object objectValue = row.get( valueKey );
- if ( objectValue instanceof List )
- {
- List value = (List) objectValue;
- List expectedValues = (List) expected.get( key );
- assertEquals( "Results for '" + key + "' should have size " + expectedValues.size() + " but was " +
- value.size(), value.size(), expectedValues.size() );
- assertThat( value, containsInAnyOrder( expectedValues.toArray() ) );
- }
- else
- {
- String value = objectValue.toString();
- String expectedValue = expected.get( key ).toString();
- assertTrue(
- String.format( "Wrong value for '%s', expected '%s', got '%s'", key, expectedValue, value),
- value.equals( expectedValue )
- );
- }
- }
+ latch.finishAndWaitForAllToFinish();
+
+ userThread.closeAndAssertTransactionTermination();
+
+ assertEmpty( adminSubject, "MATCH (n:Test) RETURN n.name AS name" );
+ }
+
+ @SuppressWarnings( "unchecked" )
+ TransportConnection startBoltSession( String username, String password ) throws Exception
+ {
+ TransportConnection connection = new SocketConnection();
+ HostnamePort address = new HostnamePort( "localhost:7687" );
+ Map authToken = map( "principal", username, "credentials", password, "scheme", "basic" );
+
+ connection.connect( address ).send( TransportTestUtil.acceptedVersions( 1, 0, 0, 0 ) )
+ .send( TransportTestUtil.chunk( init( "TestClient/1.1", authToken ) ) );
+
+ assertThat( connection, eventuallyReceives( new byte[]{0, 0, 0, 1} ) );
+ assertThat( connection, eventuallyReceives( msgSuccess() ) );
+ return connection;
}
- public static class CountResult
+ private static class CountResult
{
public final String count;
@@ -418,7 +430,7 @@ public static class CountResult
}
}
- public static class ClassWithProcedures
+ static class ClassWithProcedures
{
@Context
public GraphDatabaseService db;
@@ -490,7 +502,7 @@ static class LatchedRunnables implements AutoCloseable
Runnable runBefore;
Runnable runAfter;
- public LatchedRunnables( DoubleLatch doubleLatch, Runnable runBefore, Runnable runAfter )
+ LatchedRunnables( DoubleLatch doubleLatch, Runnable runBefore, Runnable runAfter )
{
this.doubleLatch = doubleLatch;
this.runBefore = runBefore;
@@ -504,7 +516,7 @@ public void close() throws Exception
}
}
- public static void setTestLatch( LatchedRunnables testLatch )
+ static void setTestLatch( LatchedRunnables testLatch )
{
ClassWithProcedures.testLatch.set( testLatch );
}
diff --git a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTProceduresIT.java b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTAuthProceduresIT.java
similarity index 85%
rename from enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTProceduresIT.java
rename to enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTAuthProceduresIT.java
index 82d3a4abf727b..d456102e92886 100644
--- a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTProceduresIT.java
+++ b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTAuthProceduresIT.java
@@ -21,18 +21,18 @@
import org.junit.Rule;
-import org.neo4j.server.security.enterprise.auth.AuthProceduresTestLogic;
+import org.neo4j.server.security.enterprise.auth.AuthProceduresInteractionTestBase;
import org.neo4j.server.security.enterprise.auth.NeoInteractionLevel;
import org.neo4j.test.rule.SuppressOutput;
import static org.neo4j.test.rule.SuppressOutput.suppressAll;
-public class NeoFullRESTProceduresIT extends AuthProceduresTestLogic
+public class RESTAuthProceduresIT extends AuthProceduresInteractionTestBase
{
@Rule
public SuppressOutput suppressOutput = suppressAll();
- public NeoFullRESTProceduresIT()
+ public RESTAuthProceduresIT()
{
super();
CHANGE_PWD_ERR_MSG = "User is required to change their password.";
@@ -43,6 +43,6 @@ public NeoFullRESTProceduresIT()
@Override
public NeoInteractionLevel setUpNeoServer() throws Throwable
{
- return new NeoFullRESTInteraction();
+ return new RESTInteraction();
}
}
diff --git a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTScenariosIT.java b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTAuthScenariosIT.java
similarity index 85%
rename from enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTScenariosIT.java
rename to enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTAuthScenariosIT.java
index 2abbb1bb57785..b3a37f0759d8e 100644
--- a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTScenariosIT.java
+++ b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTAuthScenariosIT.java
@@ -21,18 +21,18 @@
import org.junit.Rule;
-import org.neo4j.server.security.enterprise.auth.AuthScenariosLogic;
+import org.neo4j.server.security.enterprise.auth.AuthScenariosInteractionTestBase;
import org.neo4j.server.security.enterprise.auth.NeoInteractionLevel;
import org.neo4j.test.rule.SuppressOutput;
import static org.neo4j.test.rule.SuppressOutput.suppressAll;
-public class NeoFullRESTScenariosIT extends AuthScenariosLogic
+public class RESTAuthScenariosIT extends AuthScenariosInteractionTestBase
{
@Rule
public SuppressOutput suppressOutput = suppressAll();
- public NeoFullRESTScenariosIT()
+ public RESTAuthScenariosIT()
{
super();
CHANGE_PWD_ERR_MSG = "User is required to change their password.";
@@ -43,6 +43,6 @@ public NeoFullRESTScenariosIT()
@Override
protected NeoInteractionLevel setUpNeoServer() throws Throwable
{
- return new NeoFullRESTInteraction();
+ return new RESTInteraction();
}
}
diff --git a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTBuiltInProceduresIT.java b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTBuiltInProceduresIT.java
new file mode 100644
index 0000000000000..e49fc8d7b8b1a
--- /dev/null
+++ b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTBuiltInProceduresIT.java
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2002-2016 "Neo Technology,"
+ * Network Engine for Objects in Lund AB [http://neotechnology.com]
+ *
+ * This file is part of Neo4j.
+ *
+ * Neo4j is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+package org.neo4j.server.rest.security;
+
+import org.junit.Rule;
+
+import org.neo4j.server.security.enterprise.auth.BuiltInProceduresInteractionTestBase;
+import org.neo4j.server.security.enterprise.auth.NeoInteractionLevel;
+import org.neo4j.test.rule.SuppressOutput;
+
+import static org.neo4j.test.rule.SuppressOutput.suppressAll;
+
+public class RESTBuiltInProceduresIT extends BuiltInProceduresInteractionTestBase
+{
+ @Rule
+ public SuppressOutput suppressOutput = suppressAll();
+
+ public RESTBuiltInProceduresIT()
+ {
+ super();
+ CHANGE_PWD_ERR_MSG = "User is required to change their password.";
+ PWD_CHANGE_CHECK_FIRST = true;
+ IS_EMBEDDED = false;
+ }
+
+ @Override
+ public NeoInteractionLevel setUpNeoServer() throws Throwable
+ {
+ return new RESTInteraction();
+ }
+}
diff --git a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTInteraction.java b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTInteraction.java
similarity index 94%
rename from enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTInteraction.java
rename to enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTInteraction.java
index 12b12f1b8afde..37e4f087079d8 100644
--- a/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/NeoFullRESTInteraction.java
+++ b/enterprise/server-enterprise/src/test/java/org/neo4j/server/rest/security/RESTInteraction.java
@@ -29,7 +29,6 @@
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
-import java.util.List;
import java.util.Map;
import java.util.TreeMap;
import java.util.function.Consumer;
@@ -59,14 +58,14 @@
import static org.neo4j.graphdb.factory.GraphDatabaseSettings.boltConnector;
import static org.neo4j.kernel.api.security.AuthToken.newBasicAuthToken;
-public class NeoFullRESTInteraction extends CommunityServerTestBase implements NeoInteractionLevel
+class RESTInteraction extends CommunityServerTestBase implements NeoInteractionLevel
{
- String COMMIT_PATH = "db/data/transaction/commit";
- String POST = "POST";
+ private String COMMIT_PATH = "db/data/transaction/commit";
+ private String POST = "POST";
EnterpriseAuthManager authManager;
- public NeoFullRESTInteraction() throws IOException
+ RESTInteraction() throws IOException
{
server = EnterpriseServerBuilder.server()
.withProperty( boltConnector( "0" ).enabled.name(), "true" )
@@ -211,18 +210,18 @@ private String parseErrorMessage( HTTP.Response response )
return "";
}
- protected String commitURL()
+ private String commitURL()
{
return server.baseUri().resolve( COMMIT_PATH ).toString();
}
- class RESTResult implements ResourceIterator>
+ private class RESTResult implements ResourceIterator>
{
private JsonNode data;
private JsonNode columns;
private int index = 0;
- public RESTResult( JsonNode fullResult )
+ RESTResult( JsonNode fullResult )
{
this.data = fullResult.get( "data" );
this.columns = fullResult.get( "columns" );
@@ -244,7 +243,7 @@ public boolean hasNext()
public Map next()
{
JsonNode row = data.get( index++ ).get( "row" );
- TreeMap map = new TreeMap();
+ TreeMap map = new TreeMap<>();
for ( int i = 0; i < columns.size(); i++ )
{
String key = columns.get( i ).asText();
@@ -270,7 +269,7 @@ else if ( valueNode instanceof ObjectNode )
else if ( valueNode instanceof ArrayNode )
{
ArrayNode aNode = (ArrayNode) valueNode;
- ArrayList listValue = new ArrayList( aNode.size() );
+ ArrayList listValue = new ArrayList<>( aNode.size() );
for ( int j = 0; j < aNode.size(); j++ )
{
listValue.add( aNode.get( j ).asText() );
@@ -297,7 +296,7 @@ else if ( valueNode instanceof LongNode )
private Map mapValue( Iterator columns, JsonNode node )
{
- TreeMap map = new TreeMap();
+ TreeMap map = new TreeMap<>();
while ( columns.hasNext() )
{
String key = columns.next();