You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cayenne.apache.org by nt...@apache.org on 2022/07/07 18:48:44 UTC

[cayenne] 01/05: CAY-2744 Remove ROP support - delete ROP modules

This is an automated email from the ASF dual-hosted git repository.

ntimofeev pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/cayenne.git

commit 984bbf22bd00d42c0b86c12c3542b8f1e735f952
Author: Nikita Timofeev <st...@gmail.com>
AuthorDate: Thu Jul 7 18:24:31 2022 +0300

    CAY-2744 Remove ROP support
     - delete ROP modules
---
 cayenne-client-jetty/pom.xml                       | 147 -----
 .../rop/client/ClientJettyHttp2Module.java         |  44 --
 .../rop/client/ClientJettyHttpModule.java          |  40 --
 .../rop/client/JettyClientModuleProvider.java      |  46 --
 .../rop/JettyHttp2ClientConnectionProvider.java    |  59 --
 .../rop/JettyHttpClientConnectionProvider.java     | 128 ----
 .../cayenne/rop/http/JettyHttpROPConnector.java    | 190 ------
 ...guration.rop.client.CayenneClientModuleProvider |  20 -
 .../rop/client/JettyModuleProviderTest.java        |  35 --
 .../cayenne/rop/http/JettyHttpROPConnectorIT.java  | 134 ----
 .../org/apache/cayenne/util/Http2TestServer.java   | 127 ----
 cayenne-client/pom.xml                             | 135 ----
 .../rop/client/CayenneClientModuleProvider.java    |  29 -
 .../rop/client/CayenneContextFactory.java          |  67 --
 .../rop/client/ClientChannelProvider.java          |  47 --
 .../configuration/rop/client/ClientConstants.java  |  50 --
 .../configuration/rop/client/ClientModule.java     |  69 ---
 .../configuration/rop/client/ClientRuntime.java    |  66 --
 .../rop/client/ClientRuntimeBuilder.java           | 147 -----
 .../client/LocalClientServerChannelProvider.java   |  51 --
 .../rop/client/LocalConnectionProvider.java        |  43 --
 .../client/MainCayenneClientModuleProvider.java    |  46 --
 .../org/apache/cayenne/remote/BaseConnection.java  | 125 ----
 .../org/apache/cayenne/remote/ClientChannel.java   | 314 ----------
 .../apache/cayenne/remote/ClientConnection.java    |  47 --
 .../remote/hessian/ClientSerializerFactory.java    |  75 ---
 .../remote/hessian/DataRowDeserializer.java        |  81 ---
 .../remote/hessian/service/HessianUtil.java        |  87 ---
 .../java/org/apache/cayenne/remote/package.html    |  24 -
 .../cayenne/remote/service/LocalConnection.java    | 144 -----
 .../apache/cayenne/rop/HttpClientConnection.java   | 134 ----
 .../cayenne/rop/HttpClientConnectionProvider.java  |  73 ---
 .../org/apache/cayenne/rop/ProxyRemoteService.java |  76 ---
 .../java/org/apache/cayenne/rop/ROPConnector.java  |  52 --
 .../main/java/org/apache/cayenne/rop/ROPUtil.java  | 151 -----
 .../ClientHessianSerializationServiceProvider.java |  39 --
 .../apache/cayenne/rop/http/HttpROPConnector.java  | 166 -----
 ...guration.rop.client.CayenneClientModuleProvider |  20 -
 .../apache/cayenne/CayenneContextCayenneIT.java    |  51 --
 .../CayenneContextClientChannelEventsIT.java       | 353 -----------
 .../cayenne/CayenneContextDeleteRulesIT.java       | 123 ----
 .../org/apache/cayenne/CayenneContextEJBQLIT.java  |  93 ---
 .../CayenneContextGraphDiffCompressorIT.java       | 103 ----
 .../java/org/apache/cayenne/CayenneContextIT.java  | 342 -----------
 .../cayenne/CayenneContextInheritanceIT.java       | 146 -----
 .../cayenne/CayenneContextMapRelationshipIT.java   | 119 ----
 .../cayenne/CayenneContextMeaningfulPKIT.java      |  71 ---
 .../cayenne/CayenneContextMergeHandlerIT.java      |  98 ---
 .../cayenne/CayenneContextNamedQueryCachingIT.java | 133 ----
 .../CayenneContextPaginatedListCachingIT.java      |  75 ---
 .../apache/cayenne/CayenneContextPrimitiveIT.java  | 134 ----
 .../apache/cayenne/CayenneContextReflexiveIT.java  |  94 ---
 .../cayenne/CayenneContextRefreshQueryIT.java      |  79 ---
 .../cayenne/CayenneContextRelationshipsIT.java     | 102 ----
 .../cayenne/CayenneContextSQLTemplateIT.java       |  50 --
 .../cayenne/CayenneContextServerDiffsIT.java       | 163 -----
 .../apache/cayenne/CayenneContextValidationIT.java |  86 ---
 .../cayenne/CayenneContextWithDataContextIT.java   | 465 --------------
 .../test/java/org/apache/cayenne/DataRowTest.java  |  51 --
 .../org/apache/cayenne/NestedCayenneContextIT.java | 680 ---------------------
 .../cayenne/NestedCayenneContextTooneIT.java       | 222 -------
 .../apache/cayenne/ObjectContextChangeLogTest.java |  48 --
 .../test/java/org/apache/cayenne/ObjectIdTest.java |  84 ---
 .../cayenne/PersistentObjectInContextIT.java       | 151 -----
 .../cayenne/access/ClientServerChannelIT.java      | 263 --------
 .../cayenne/access/ClientServerChannelQueryIT.java | 241 --------
 .../org/apache/cayenne/access/types/EnumTest.java  | 113 ----
 .../org/apache/cayenne/cay_2641/Cay2641IT.java     |  97 ---
 .../rop/client/ClientLocalRuntimeTest.java         |  84 ---
 .../configuration/rop/client/ClientModuleTest.java |  98 ---
 .../rop/client/ClientRuntimeBuilderTest.java       | 160 -----
 .../rop/client/ClientRuntimeTest.java              | 118 ----
 .../MainCayenneClientModuleProviderTest.java       |  35 --
 .../org/apache/cayenne/event/EventSubjectTest.java |  40 --
 .../org/apache/cayenne/graph/NodeDiffTest.java     |  58 --
 .../cayenne/map/ClientEntityResolverTest.java      |  66 --
 .../cayenne/map/ClientObjectRelationshipTest.java  |  48 --
 .../java/org/apache/cayenne/map/DataMapTest.java   |  42 --
 .../java/org/apache/cayenne/map/DbEntityTest.java  |  58 --
 .../java/org/apache/cayenne/map/EntityTest.java    |  65 --
 .../apache/cayenne/query/ClientExpressionIT.java   | 346 -----------
 .../apache/cayenne/query/ClientObjectSelectIT.java | 156 -----
 .../query/ClientSelectQueryExpressionIT.java       |  73 ---
 .../apache/cayenne/query/ObjectIdQueryTest.java    |  42 --
 .../apache/cayenne/query/PrefetchTreeNodeTest.java | 159 -----
 .../org/apache/cayenne/query/RefreshQueryTest.java |  40 --
 .../cayenne/query/RelationshipQueryTest.java       |  42 --
 .../org/apache/cayenne/query/SQLTemplateTest.java  |  51 --
 .../org/apache/cayenne/query/SelectById_IT.java    |  57 --
 .../cayenne/query/SelectQueryAbstractEntityIT.java | 113 ----
 .../cayenne/remote/CayenneContextDeletionIT.java   |  63 --
 .../cayenne/remote/ClientChannelServerDiffsIT.java | 281 ---------
 .../remote/ClientChannelServerDiffsListener1.java  |  37 --
 .../apache/cayenne/remote/ClientChannelTest.java   | 251 --------
 .../apache/cayenne/remote/LocalConnectionTest.java |  49 --
 .../cayenne/remote/MockClientConnection.java       |  68 ---
 .../cayenne/remote/NestedObjectContextLocalIT.java |  84 ---
 .../remote/NestedObjectContextParentEventsIT.java  |  80 ---
 .../remote/NestedObjectContextPeerEventsIT.java    | 168 -----
 .../remote/NestedObjectContextRollbackIT.java      |  98 ---
 .../cayenne/remote/ROPPrefetchToManyMapIT.java     |  81 ---
 .../cayenne/remote/RelationshipChangeIT.java       |  86 ---
 .../apache/cayenne/remote/RemoteCallbacksIT.java   | 142 -----
 .../apache/cayenne/remote/RemoteCayenneCase.java   |  66 --
 .../remote/RemoteIncrementalFaultListIT.java       | 273 ---------
 .../apache/cayenne/remote/RemoteRollbackIT.java    | 178 ------
 .../org/apache/cayenne/remote/SyncMessageTest.java |  85 ---
 .../org/apache/cayenne/remote/ValueInjectorIT.java | 100 ---
 .../rop/http/HessianROPSerializationServiceIT.java | 114 ----
 .../apache/cayenne/unit/UnitLocalConnection.java   |  63 --
 .../apache/cayenne/unit/di/client/ClientCase.java  |  59 --
 .../client/ClientCaseCayenneContextProvider.java   |  36 --
 .../client/ClientCaseClientConnectionProvider.java |  35 --
 .../unit/di/client/ClientCaseContextsSync.java     |  70 ---
 .../unit/di/client/ClientCaseLifecycleManager.java |  67 --
 .../cayenne/unit/di/client/ClientCaseModule.java   |  62 --
 .../di/client/ClientCaseObjectContextProvider.java |  35 --
 .../unit/di/client/ClientCaseProperties.java       |  36 --
 .../cayenne/unit/di/client/ClientCaseSelfIT.java   |  53 --
 .../unit/di/client/ClientRuntimeProperty.java      |  36 --
 .../unit/di/client/ClientRuntimeProvider.java      |  62 --
 .../client/ClientRuntimeProviderContextsSync.java  |  42 --
 .../di/client/ClientServerChannelProvider.java     |  42 --
 .../client/ClientServerDataChannelDecorator.java   |  90 ---
 .../client/ClientServerDataChannelInterceptor.java |  75 ---
 .../InterceptingClientServerChannelProvider.java   |  38 --
 .../apache/cayenne/util/GenericResponseTest.java   |  64 --
 .../org/apache/cayenne/util/ListResponseTest.java  |  42 --
 .../cayenne/util/ObjectDetachOperationIT.java      | 120 ----
 .../cayenne/util/PersistentObjectListTest.java     |  79 ---
 .../util/ShallowMergeOperation_ClientIT.java       | 214 -------
 cayenne-protostuff/pom.xml                         | 157 -----
 ...bjectContextChangeLogSubListMessageFactory.java |  38 --
 .../ProtostuffServerModuleProvider.java            |  49 --
 .../rop/client/ProtostuffClientModuleProvider.java |  46 --
 .../configuration/rop/client/ProtostuffModule.java |  48 --
 .../cayenne/query/PrefetchTreeNodeSchema.java      | 157 -----
 .../ProtostuffROPSerializationService.java         |  92 ---
 .../org/apache/cayenne/rop/protostuff/Wrapper.java |  40 --
 ...guration.rop.client.CayenneClientModuleProvider |  20 -
 ...onfiguration.server.CayenneServerModuleProvider |  20 -
 ...tContextChangeLogSubListMessageFactoryTest.java |  55 --
 .../rop/client/ProtostuffModuleProviderTest.java   |  42 --
 .../cayenne/query/PrefetchTreeNodeSchemaTest.java  |  61 --
 .../remote/service/ProtostuffLocalConnection.java  |  78 ---
 .../service/ProtostuffLocalConnectionProvider.java |  40 --
 .../ProtostuffPersistentObjectCollectionsTest.java | 211 -------
 .../rop/protostuff/ProtostuffProperties.java       |  32 -
 .../ProtostuffROPSerializationServiceIT.java       |  83 ---
 .../protostuff/ProtostuffROPSerializationTest.java | 136 -----
 .../apache/cayenne/rop/protostuff/RuntimeBase.java |  67 --
 .../rop/protostuff/persistent/ClientMtTable1.java  |  31 -
 .../rop/protostuff/persistent/ClientMtTable2.java  |  31 -
 .../rop/protostuff/persistent/MtTable1.java        |  28 -
 .../rop/protostuff/persistent/MtTable2.java        |  28 -
 .../persistent/auto/_ClientMtTable1.java           | 178 ------
 .../persistent/auto/_ClientMtTable2.java           |  62 --
 .../rop/protostuff/persistent/auto/_MtTable1.java  | 212 -------
 .../rop/protostuff/persistent/auto/_MtTable2.java  | 106 ----
 .../src/test/resources/cayenne-protostuff.xml      |  16 -
 .../src/test/resources/protostuff.map.xml          |  42 --
 cayenne-rop-server/pom.xml                         |  91 ---
 .../java/org/apache/cayenne/CayenneContext.java    | 381 ------------
 .../cayenne/CayenneContextChildDiffLoader.java     | 140 -----
 .../apache/cayenne/CayenneContextGraphManager.java | 386 ------------
 .../apache/cayenne/CayenneContextMergeHandler.java | 273 ---------
 .../apache/cayenne/CayenneContextQueryAction.java  | 186 ------
 .../configuration/rop/server/ROPServerModule.java  |  68 ---
 .../rop/server/ROPServerModuleProvider.java        |  48 --
 .../apache/cayenne/remote/BootstrapMessage.java    |  36 --
 .../org/apache/cayenne/remote/ClientMessage.java   |  31 -
 .../apache/cayenne/remote/IncrementalQuery.java    |  73 ---
 .../cayenne/remote/IncrementalSelectQuery.java     | 234 -------
 .../org/apache/cayenne/remote/QueryMessage.java    |  55 --
 .../java/org/apache/cayenne/remote/RangeQuery.java | 156 -----
 .../cayenne/remote/RemoteIncrementalFaultList.java | 669 --------------------
 .../org/apache/cayenne/remote/RemoteService.java   |  54 --
 .../org/apache/cayenne/remote/RemoteSession.java   | 154 -----
 .../org/apache/cayenne/remote/SyncMessage.java     |  91 ---
 .../remote/hessian/CayenneSerializerFactory.java   |  43 --
 .../cayenne/remote/hessian/HessianConfig.java      | 152 -----
 .../remote/hessian/service/HessianService.java     |  64 --
 .../hessian/service/ServerDataRowSerializer.java   |  56 --
 .../ServerPersistentObjectListSerializer.java      |  50 --
 .../hessian/service/ServerSerializerFactory.java   |  71 ---
 .../cayenne/remote/service/BaseRemoteService.java  | 197 ------
 .../cayenne/remote/service/DispatchHelper.java     |  49 --
 .../cayenne/remote/service/HttpRemoteService.java  | 134 ----
 .../remote/service/MissingSessionException.java    |  38 --
 .../cayenne/remote/service/ServerSession.java      |  49 --
 .../rop/HessianROPSerializationService.java        |  69 ---
 .../java/org/apache/cayenne/rop/ROPConstants.java  |  33 -
 .../org/apache/cayenne/rop/ROPRequestContext.java  | 107 ----
 .../cayenne/rop/ROPSerializationService.java       |  39 --
 .../java/org/apache/cayenne/rop/ROPServlet.java    | 136 -----
 .../ServerHessianSerializationServiceProvider.java |  59 --
 .../cayenne/rop/ServerHttpRemoteService.java       |  47 --
 ...onfiguration.server.CayenneServerModuleProvider |  20 -
 .../cayenne/CayenneContextGraphManagerTest.java    |  67 --
 .../configuration/rop/server/MockModule1.java      |  30 -
 .../configuration/rop/server/MockModule2.java      |  32 -
 .../rop/server/MockRequestHandler.java             |  35 --
 .../rop/server/ROPHessianServlet_ConfigModule.java |  38 --
 .../rop/server/ROPServerModuleProviderTest.java    |  34 --
 .../configuration/rop/server/ROPServletTest.java   | 194 ------
 .../apache/cayenne/remote/MockRemoteService.java   |  40 --
 .../apache/cayenne/remote/RemoteSessionTest.java   |  58 --
 .../cayenne/remote/hessian/HessianConfigTest.java  |  61 --
 .../hessian/MockAbstractSerializerFactory.java     |  51 --
 .../remote/hessian/service/HessianServiceTest.java |  73 ---
 .../remote/service/BaseRemoteServiceTest.java      | 142 -----
 .../cayenne/remote/service/DispatchHelperTest.java |  54 --
 .../service/MockUnserializableException.java       |  24 -
 pom.xml                                            |   4 -
 214 files changed, 21515 deletions(-)

diff --git a/cayenne-client-jetty/pom.xml b/cayenne-client-jetty/pom.xml
deleted file mode 100644
index 3ba80e052..000000000
--- a/cayenne-client-jetty/pom.xml
+++ /dev/null
@@ -1,147 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!-- Licensed to the Apache Software Foundation (ASF) under one or more contributor
-	license agreements. See the NOTICE file distributed with this work for additional
-	information regarding copyright ownership. The ASF licenses this file to
-	you under the Apache License, Version 2.0 (the "License"); you may not use
-	this file except in compliance with the License. You may obtain a copy of
-	the License at https://www.apache.org/licenses/LICENSE-2.0 Unless required
-	by applicable law or agreed to in writing, software distributed under the
-	License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS
-	OF ANY KIND, either express or implied. See the License for the specific
-	language governing permissions and limitations under the License. -->
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
-    <modelVersion>4.0.0</modelVersion>
-
-    <parent>
-        <artifactId>cayenne-parent</artifactId>
-        <groupId>org.apache.cayenne</groupId>
-        <version>4.3.M1-SNAPSHOT</version>
-    </parent>
-
-    <artifactId>cayenne-client-jetty</artifactId>
-    <name>cayenne-client-jetty: Cayenne ROP Client (Jetty)</name>
-    <packaging>jar</packaging>
-
-    <properties>
-        <jetty.version>9.4.41.v20210516</jetty.version>
-    </properties>
-
-    <dependencyManagement>
-        <dependencies>
-            <!-- Jetty client -->
-            <dependency>
-                <groupId>org.eclipse.jetty</groupId>
-                <artifactId>jetty-client</artifactId>
-                <version>${jetty.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.eclipse.jetty.http2</groupId>
-                <artifactId>http2-client</artifactId>
-                <version>${jetty.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.eclipse.jetty.http2</groupId>
-                <artifactId>http2-http-client-transport</artifactId>
-                <version>${jetty.version}</version>
-            </dependency>
-
-            <!-- Jetty server test dependencies -->
-            <dependency>
-                <groupId>org.eclipse.jetty.http2</groupId>
-                <artifactId>http2-server</artifactId>
-                <version>${jetty.version}</version>
-                <scope>test</scope>
-            </dependency>
-            <dependency>
-                <groupId>org.eclipse.jetty</groupId>
-                <artifactId>jetty-servlet</artifactId>
-                <version>${jetty.version}</version>
-                <scope>test</scope>
-            </dependency>
-            <dependency>
-                <groupId>org.eclipse.jetty</groupId>
-                <artifactId>jetty-servlets</artifactId>
-                <version>${jetty.version}</version>
-                <scope>test</scope>
-            </dependency>
-        </dependencies>
-    </dependencyManagement>
-
-    <dependencies>
-        <!-- Compile dependencies -->
-        <dependency>
-            <groupId>org.apache.cayenne</groupId>
-            <artifactId>cayenne-client</artifactId>
-            <version>${project.version}</version>
-        </dependency>
-        <dependency>
-            <groupId>org.slf4j</groupId>
-            <artifactId>slf4j-api</artifactId>
-        </dependency>
-
-        <!-- Jetty client -->
-        <dependency>
-            <groupId>org.eclipse.jetty</groupId>
-            <artifactId>jetty-client</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>org.eclipse.jetty.http2</groupId>
-            <artifactId>http2-client</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>org.eclipse.jetty.http2</groupId>
-            <artifactId>http2-http-client-transport</artifactId>
-        </dependency>
-
-        <!--Test dependencies-->
-        <dependency>
-            <groupId>org.apache.cayenne</groupId>
-            <artifactId>cayenne-server</artifactId>
-            <version>${project.version}</version>
-            <type>test-jar</type>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.eclipse.jetty.http2</groupId>
-            <artifactId>http2-server</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.eclipse.jetty</groupId>
-            <artifactId>jetty-servlet</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.eclipse.jetty</groupId>
-            <artifactId>jetty-servlets</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>junit</groupId>
-            <artifactId>junit</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.slf4j</groupId>
-            <artifactId>slf4j-simple</artifactId>
-            <scope>test</scope>
-        </dependency>
-    </dependencies>
-
-    <build>
-        <plugins>
-            <!-- This ensures LICENSE and NOTICE inclusion in all jars -->
-            <plugin>
-                <artifactId>maven-remote-resources-plugin</artifactId>
-                <executions>
-                    <execution>
-                        <goals>
-                            <goal>process</goal>
-                        </goals>
-                    </execution>
-                </executions>
-            </plugin>
-        </plugins>
-    </build>
-
-</project>
\ No newline at end of file
diff --git a/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/ClientJettyHttp2Module.java b/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/ClientJettyHttp2Module.java
deleted file mode 100644
index d8205a119..000000000
--- a/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/ClientJettyHttp2Module.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.di.Binder;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.rop.JettyHttp2ClientConnectionProvider;
-import org.apache.cayenne.rop.http.JettyHttpROPConnector;
-
-/**
- * This is HTTP/2 implementation of ROP Client.
- * <p>
- * This module uses {@link JettyHttpROPConnector} initialized by {@link JettyHttp2ClientConnectionProvider}
- * without ALPN by default.
- * <p>
- * In order to use it with ALPN you have to set {@link ClientConstants#ROP_SERVICE_USE_ALPN_PROPERTY} to true
- * and provide the alpn-boot-XXX.jar into the bootstrap classpath.
- */
-public class ClientJettyHttp2Module implements Module {
-
-    @Override
-    public void configure(Binder binder) {
-        binder.bind(ClientConnection.class).toProvider(JettyHttp2ClientConnectionProvider.class);
-    }
-
-}
diff --git a/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/ClientJettyHttpModule.java b/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/ClientJettyHttpModule.java
deleted file mode 100644
index 8ef81ba01..000000000
--- a/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/ClientJettyHttpModule.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.di.Binder;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.rop.JettyHttpClientConnectionProvider;
-import org.apache.cayenne.rop.http.JettyHttpROPConnector;
-
-/**
- * This is HTTP/1.1 implementation of ROP Client.
- * <p>
- * This module uses {@link JettyHttpROPConnector} initialized by {@link JettyHttpClientConnectionProvider}.
- */
-public class ClientJettyHttpModule implements Module {
-
-    @Override
-    public void configure(Binder binder) {
-        binder.bind(ClientConnection.class).toProvider(JettyHttpClientConnectionProvider.class);
-    }
-
-}
\ No newline at end of file
diff --git a/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/JettyClientModuleProvider.java b/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/JettyClientModuleProvider.java
deleted file mode 100644
index 9ec5d5ef6..000000000
--- a/cayenne-client-jetty/src/main/java/org/apache/cayenne/configuration/rop/client/JettyClientModuleProvider.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import java.util.Collection;
-import java.util.Collections;
-
-import org.apache.cayenne.di.Module;
-
-/**
- * @since 4.0
- */
-public class JettyClientModuleProvider implements CayenneClientModuleProvider {
-
-    @Override
-    public Module module() {
-        return new ClientJettyHttpModule();
-    }
-
-    @Override
-    public Class<? extends Module> moduleType() {
-        return ClientJettyHttpModule.class;
-    }
-
-    @Override
-    public Collection<Class<? extends Module>> overrides() {
-        return Collections.singletonList(ClientModule.class);
-    }
-}
diff --git a/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/JettyHttp2ClientConnectionProvider.java b/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/JettyHttp2ClientConnectionProvider.java
deleted file mode 100644
index fb5328011..000000000
--- a/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/JettyHttp2ClientConnectionProvider.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.rop;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.configuration.rop.client.ClientConstants;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.rop.http.JettyHttpROPConnector;
-import org.eclipse.jetty.client.HttpClient;
-import org.eclipse.jetty.http2.client.HTTP2Client;
-import org.eclipse.jetty.http2.client.http.HttpClientTransportOverHTTP2;
-import org.eclipse.jetty.util.ssl.SslContextFactory;
-
-/**
- * This {@link Provider} initializes HTTP/2 {@link ClientConnection} through {@link JettyHttpROPConnector} which uses
- * {@link org.eclipse.jetty.client.HttpClient} over {@link org.eclipse.jetty.http2.client.HTTP2Client}.
- * It works without ALPN by default.
- * <p>
- * In order to use it with ALPN you have to set {@link ClientConstants#ROP_SERVICE_USE_ALPN_PROPERTY} to true
- * and provide the alpn-boot-XXX.jar into the bootstrap classpath.
- */
-public class JettyHttp2ClientConnectionProvider extends JettyHttpClientConnectionProvider {
-
-    @Override
-    protected HttpClient initJettyHttpClient() {
-        try {
-            HttpClientTransportOverHTTP2 http2 = new HttpClientTransportOverHTTP2(new HTTP2Client());
-
-            boolean useALPN = runtimeProperties.getBoolean(ClientConstants.ROP_SERVICE_USE_ALPN_PROPERTY, false);
-            http2.setUseALPN(useALPN);
-
-            HttpClient httpClient = new HttpClient(http2, new SslContextFactory());
-            httpClient.start();
-
-            return httpClient;
-        } catch (Exception e) {
-            throw new CayenneRuntimeException("Exception while starting Jetty HttpClient over HTTP/2.", e);
-        }
-    }
-
-}
diff --git a/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/JettyHttpClientConnectionProvider.java b/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/JettyHttpClientConnectionProvider.java
deleted file mode 100644
index 62d0bbd23..000000000
--- a/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/JettyHttpClientConnectionProvider.java
+++ /dev/null
@@ -1,128 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.rop;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.ConfigurationException;
-import org.apache.cayenne.configuration.RuntimeProperties;
-import org.apache.cayenne.configuration.rop.client.ClientConstants;
-import org.apache.cayenne.di.DIRuntimeException;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.rop.http.JettyHttpROPConnector;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-import org.eclipse.jetty.client.HttpClient;
-import org.eclipse.jetty.client.api.AuthenticationStore;
-import org.eclipse.jetty.client.util.BasicAuthentication;
-import org.eclipse.jetty.util.ssl.SslContextFactory;
-
-import java.net.URI;
-
-/**
- * This {@link Provider} initializes HTTP/1.1 {@link ClientConnection} through {@link JettyHttpROPConnector} which uses
- * {@link org.eclipse.jetty.client.HttpClient}.
- */
-public class JettyHttpClientConnectionProvider implements Provider<ClientConnection> {
-
-    private static final Logger logger = LoggerFactory.getLogger(JettyHttpROPConnector.class);
-
-    @Inject
-    protected RuntimeProperties runtimeProperties;
-
-    @Inject
-    protected ROPSerializationService serializationService;
-
-    @Override
-    public ClientConnection get() throws DIRuntimeException {
-        String sharedSession = runtimeProperties
-                .get(ClientConstants.ROP_SERVICE_SHARED_SESSION_PROPERTY);
-
-        JettyHttpROPConnector ropConnector = createJettyHttpRopConnector();
-        ProxyRemoteService remoteService = new ProxyRemoteService(serializationService, ropConnector);
-
-        HttpClientConnection clientConnection = new HttpClientConnection(remoteService, sharedSession);
-        ropConnector.setClientConnection(clientConnection);
-
-        return clientConnection;
-    }
-
-    protected JettyHttpROPConnector createJettyHttpRopConnector() {
-        String url = runtimeProperties.get(ClientConstants.ROP_SERVICE_URL_PROPERTY);
-        if (url == null) {
-            throw new ConfigurationException(
-                    "No property defined for '%s', can't initialize connection",
-                    ClientConstants.ROP_SERVICE_URL_PROPERTY);
-        }
-
-        String username = runtimeProperties.get(ClientConstants.ROP_SERVICE_USERNAME_PROPERTY);
-        long readTimeout = runtimeProperties.getLong(
-                ClientConstants.ROP_SERVICE_TIMEOUT_PROPERTY,
-                -1L);
-
-        HttpClient httpClient = initJettyHttpClient();
-
-        addBasicAuthentication(httpClient, url, username);
-
-        JettyHttpROPConnector result = new JettyHttpROPConnector(httpClient, url, username);
-
-        if (readTimeout > 0) {
-            result.setReadTimeout(readTimeout);
-        }
-
-        return result;
-    }
-
-    protected HttpClient initJettyHttpClient() {
-        try {
-            HttpClient httpClient = new HttpClient(new SslContextFactory());
-            httpClient.start();
-
-            return httpClient;
-        } catch (Exception e) {
-            throw new CayenneRuntimeException("Exception while starting Jetty HttpClient.", e);
-        }
-    }
-
-    protected void addBasicAuthentication(HttpClient httpClient, String url, String username) {
-        String password = runtimeProperties.get(ClientConstants.ROP_SERVICE_PASSWORD_PROPERTY);
-        String realm = runtimeProperties.get(ClientConstants.ROP_SERVICE_REALM_PROPERTY);
-
-        if (username != null && password != null) {
-            if (realm == null && logger.isWarnEnabled()) {
-                logger.warn("In order to use JettyClient with BASIC Authentication " +
-                        "you should provide Constants.ROP_SERVICE_REALM_PROPERTY.");
-                return;
-            }
-
-            if (logger.isInfoEnabled()) {
-                logger.info(
-                        "Adding authentication" +
-                                "\nUser: " + username +
-                                "\nRealm: " + realm);
-            }
-
-            AuthenticationStore auth = httpClient.getAuthenticationStore();
-            auth.addAuthentication(new BasicAuthentication(URI.create(url), realm, username, password));
-        }
-    }
-
-}
diff --git a/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/http/JettyHttpROPConnector.java b/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/http/JettyHttpROPConnector.java
deleted file mode 100644
index 77f11d764..000000000
--- a/cayenne-client-jetty/src/main/java/org/apache/cayenne/rop/http/JettyHttpROPConnector.java
+++ /dev/null
@@ -1,190 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.rop.http;
-
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.RemoteSession;
-import org.apache.cayenne.rop.*;
-import org.slf4j.Logger;
-import org.eclipse.jetty.client.HttpClient;
-import org.eclipse.jetty.client.api.ContentResponse;
-import org.eclipse.jetty.client.api.Request;
-import org.eclipse.jetty.client.api.Response;
-import org.eclipse.jetty.client.util.BytesContentProvider;
-import org.eclipse.jetty.client.util.InputStreamResponseListener;
-import org.eclipse.jetty.http.HttpHeader;
-import org.eclipse.jetty.http.HttpMethod;
-import org.slf4j.LoggerFactory;
-
-import java.io.ByteArrayInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.concurrent.TimeUnit;
-
-/**
- * This implementation of ROPConnector uses Jetty HTTP Client.
- * Depends on {@link ClientConnection} provider it uses HTTP/1.1 or HTTP/2 protocol.
- * <p>
- * {@link JettyHttpClientConnectionProvider} for HTTP/1.1 protocol.
- * {@link JettyHttp2ClientConnectionProvider} for HTTP/2 protocol.
- */
-public class JettyHttpROPConnector implements ROPConnector {
-
-    private static final Logger logger = LoggerFactory.getLogger(JettyHttpROPConnector.class);
-
-    public static final String SESSION_COOKIE_NAME = "JSESSIONID";
-
-    protected HttpClient httpClient;
-    protected HttpClientConnection clientConnection;
-
-    protected String url;
-    protected String username;
-
-    protected Long readTimeout = 5l;
-
-    public JettyHttpROPConnector(HttpClient httpClient, String url, String username) {
-        if (httpClient == null) {
-            throw new IllegalArgumentException("org.eclipse.jetty.client.HttpClient should be provided " +
-                    "for this ROPConnector implementation.");
-        }
-
-        this.httpClient = httpClient;
-        this.url = url;
-        this.username = username;
-    }
-
-    public void setClientConnection(HttpClientConnection clientConnection) {
-        this.clientConnection = clientConnection;
-    }
-
-    public void setReadTimeout(Long readTimeout) {
-        this.readTimeout = readTimeout;
-    }
-
-    @Override
-    public InputStream establishSession() throws IOException {
-        if (logger.isInfoEnabled()) {
-            logger.info(ROPUtil.getLogConnect(url, username, true));
-        }
-
-        try {
-            ContentResponse response = httpClient.newRequest(url)
-                    .method(HttpMethod.POST)
-                    .param(ROPConstants.OPERATION_PARAMETER, ROPConstants.ESTABLISH_SESSION_OPERATION)
-                    .timeout(readTimeout, TimeUnit.SECONDS)
-                    .send();
-
-            return new ByteArrayInputStream(response.getContent());
-        } catch (Exception e) {
-            if (e instanceof InterruptedException) {
-                Thread.currentThread().interrupt();
-            }
-
-            throw new IOException("Exception while establishing session", e);
-        }
-    }
-
-    @Override
-    public InputStream establishSharedSession(String sharedSessionName) throws IOException {
-        if (logger.isInfoEnabled()) {
-            logger.info(ROPUtil.getLogConnect(url, username, true, sharedSessionName));
-        }
-
-        try {
-            ContentResponse response = httpClient.newRequest(url)
-                    .method(HttpMethod.POST)
-                    .param(ROPConstants.OPERATION_PARAMETER, ROPConstants.ESTABLISH_SHARED_SESSION_OPERATION)
-                    .param(ROPConstants.SESSION_NAME_PARAMETER, sharedSessionName)
-                    .timeout(readTimeout, TimeUnit.SECONDS)
-                    .send();
-
-            return new ByteArrayInputStream(response.getContent());
-        } catch (Exception e) {
-            if (e instanceof InterruptedException) {
-                Thread.currentThread().interrupt();
-            }
-
-            throw new IOException("Exception while establishing shared session: " + sharedSessionName, e);
-        }
-    }
-
-    @Override
-    public InputStream sendMessage(byte[] message) throws IOException {
-        try {
-            Request request = httpClient.newRequest(url)
-                    .method(HttpMethod.POST)
-                    .header(HttpHeader.CONTENT_TYPE, "application/octet-stream")
-                    .header(HttpHeader.ACCEPT_ENCODING, "gzip")
-                    .content(new BytesContentProvider(message));
-
-            addSessionCookie(request);
-
-            InputStreamResponseListener listener = new InputStreamResponseListener();
-            request.send(listener);
-
-            /**
-             * Waits for the given timeout for the response to be available, then returns it.
-             * The wait ends as soon as all the HTTP headers have been received, without waiting for the content.
-             */
-            Response response = listener.get(readTimeout, TimeUnit.SECONDS);
-
-            if (response.getStatus() >= 300) {
-                throw new IOException(
-                        "Did not receive successful HTTP response: status code = " + response.getStatus() +
-                                ", status message = [" + response.getReason() + "]");
-            }
-
-            return listener.getInputStream();
-        } catch (Exception e) {
-            if (e instanceof InterruptedException) {
-                Thread.currentThread().interrupt();
-            }
-
-            throw new IOException("Exception while sending message", e);
-        }
-    }
-
-    @Override
-    public void close() throws IOException {
-        if (httpClient != null) {
-            if (logger.isInfoEnabled()) {
-                logger.info(ROPUtil.getLogDisconnect(url, username, true));
-            }
-
-            try {
-                httpClient.stop();
-            } catch (Exception e) {
-                throw new IOException("Exception while stopping Jetty HttpClient", e);
-            }
-        }
-    }
-
-    protected void addSessionCookie(Request request) {
-        if (clientConnection != null) {
-            RemoteSession session = clientConnection.getSession();
-
-            if (session != null && session.getSessionId() != null) {
-                request.header(HttpHeader.COOKIE, SESSION_COOKIE_NAME
-                        + "="
-                        + session.getSessionId());
-            }
-        }
-    }
-}
diff --git a/cayenne-client-jetty/src/main/resources/META-INF/services/org.apache.cayenne.configuration.rop.client.CayenneClientModuleProvider b/cayenne-client-jetty/src/main/resources/META-INF/services/org.apache.cayenne.configuration.rop.client.CayenneClientModuleProvider
deleted file mode 100644
index 10de88867..000000000
--- a/cayenne-client-jetty/src/main/resources/META-INF/services/org.apache.cayenne.configuration.rop.client.CayenneClientModuleProvider
+++ /dev/null
@@ -1,20 +0,0 @@
-##################################################################
-#   Licensed to the Apache Software Foundation (ASF) under one
-#  or more contributor license agreements.  See the NOTICE file
-#  distributed with this work for additional information
-#  regarding copyright ownership.  The ASF licenses this file
-#  to you under the Apache License, Version 2.0 (the
-#  "License"); you may not use this file except in compliance
-#  with the License.  You may obtain a copy of the License at
-#
-#    https://www.apache.org/licenses/LICENSE-2.0
-#
-#  Unless required by applicable law or agreed to in writing,
-#  software distributed under the License is distributed on an
-#  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-#  KIND, either express or implied.  See the License for the
-#  specific language governing permissions and limitations
-#  under the License.
-##################################################################
-
-org.apache.cayenne.configuration.rop.client.JettyClientModuleProvider
\ No newline at end of file
diff --git a/cayenne-client-jetty/src/test/java/org/apache/cayenne/configuration/rop/client/JettyModuleProviderTest.java b/cayenne-client-jetty/src/test/java/org/apache/cayenne/configuration/rop/client/JettyModuleProviderTest.java
deleted file mode 100644
index c142ba2de..000000000
--- a/cayenne-client-jetty/src/test/java/org/apache/cayenne/configuration/rop/client/JettyModuleProviderTest.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.unit.util.ModuleProviderChecker;
-import org.junit.Test;
-
-/**
- * @since 4.0
- */
-public class JettyModuleProviderTest {
-
-    @Test
-    public void testClientAutoLoadable() {
-        ModuleProviderChecker.testProviderPresent(JettyClientModuleProvider.class, CayenneClientModuleProvider.class);
-    }
-
-}
diff --git a/cayenne-client-jetty/src/test/java/org/apache/cayenne/rop/http/JettyHttpROPConnectorIT.java b/cayenne-client-jetty/src/test/java/org/apache/cayenne/rop/http/JettyHttpROPConnectorIT.java
deleted file mode 100644
index 28f6b4ac9..000000000
--- a/cayenne-client-jetty/src/test/java/org/apache/cayenne/rop/http/JettyHttpROPConnectorIT.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.rop.http;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.rop.ROPConstants;
-import org.apache.cayenne.util.Http2TestServer;
-import org.eclipse.jetty.client.HttpClient;
-import org.eclipse.jetty.http2.client.HTTP2Client;
-import org.eclipse.jetty.http2.client.http.HttpClientTransportOverHTTP2;
-import org.eclipse.jetty.util.ssl.SslContextFactory;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServlet;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import java.io.*;
-import java.util.stream.Collectors;
-
-import static org.junit.Assert.assertArrayEquals;
-import static org.junit.Assert.assertEquals;
-
-public class JettyHttpROPConnectorIT {
-
-    private static final String MESSAGE = "test message";
-    private static final String SEND_MESSAGE_SESSION = "send message session";
-
-    private static JettyHttpROPConnector ropConnector;
-    private static Http2TestServer server;
-
-    @BeforeClass
-    public static void setUpClass() throws Exception {
-        // Start the test server
-        class TestServlet extends HttpServlet {
-            @Override
-            protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
-                String sharedSessionName = req.getParameter(ROPConstants.SESSION_NAME_PARAMETER);
-
-                if (sharedSessionName == null) {
-                    resp.getOutputStream().write(MESSAGE.getBytes());
-                } else if (sharedSessionName.equals(SEND_MESSAGE_SESSION)) {
-                    resp.getOutputStream().write(toByteArray(req.getInputStream()));
-                } else {
-                    resp.getOutputStream().write((MESSAGE + " " + sharedSessionName).getBytes());
-                }
-            }
-        }
-
-        server = Http2TestServer.servlet(new TestServlet()).start();
-
-        ropConnector = new JettyHttpROPConnector(initJettyHttp2Client(), server.getBasePath(), null);
-    }
-
-    protected static HttpClient initJettyHttp2Client() {
-        try {
-            HttpClientTransportOverHTTP2 http2 = new HttpClientTransportOverHTTP2(new HTTP2Client());
-            http2.setUseALPN(false);
-
-            HttpClient httpClient = new HttpClient(http2, new SslContextFactory());
-            httpClient.start();
-
-            return httpClient;
-        } catch (Exception e) {
-            throw new CayenneRuntimeException("Exception while starting Jetty HttpClient over HTTP/2.", e);
-        }
-    }
-
-    @AfterClass
-    public static void tearDownClass() throws Exception {
-        server.stop();
-        ropConnector.close();
-    }
-
-    @Test
-    public void testEstablishSession() throws Exception {
-        String message = read(ropConnector.establishSession());
-        assertEquals(MESSAGE, message);
-    }
-
-    @Test
-    public void testEstablishSharedSession() throws Exception {
-        String sharedSessionName = "test session";
-        String message = read(ropConnector.establishSharedSession(sharedSessionName));
-        assertEquals(MESSAGE + " " + sharedSessionName, message);
-    }
-
-    @Test
-    public void sendMessage() throws Exception {
-        ropConnector.establishSharedSession(SEND_MESSAGE_SESSION);
-
-        byte[] message = toByteArray(ropConnector.sendMessage(MESSAGE.getBytes()));
-        assertArrayEquals(MESSAGE.getBytes(), message);
-    }
-
-    private static String read(InputStream input) throws IOException {
-        try (BufferedReader buffer = new BufferedReader(new InputStreamReader(input))) {
-            return buffer.lines().collect(Collectors.joining("\n"));
-        }
-    }
-
-    private static byte[] toByteArray(InputStream inputStream) throws IOException {
-        try (ByteArrayOutputStream baos = new ByteArrayOutputStream()) {
-
-            int reads = inputStream.read();
-            while (reads != -1) {
-                baos.write(reads);
-                reads = inputStream.read();
-            }
-
-            return baos.toByteArray();
-        }
-    }
-
-}
diff --git a/cayenne-client-jetty/src/test/java/org/apache/cayenne/util/Http2TestServer.java b/cayenne-client-jetty/src/test/java/org/apache/cayenne/util/Http2TestServer.java
deleted file mode 100644
index d12bb1c89..000000000
--- a/cayenne-client-jetty/src/test/java/org/apache/cayenne/util/Http2TestServer.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.util;
-
-import org.eclipse.jetty.http2.server.HTTP2ServerConnectionFactory;
-import org.eclipse.jetty.server.HttpConfiguration;
-import org.eclipse.jetty.server.Server;
-import org.eclipse.jetty.server.ServerConnector;
-import org.eclipse.jetty.servlet.ServletContextHandler;
-import org.eclipse.jetty.servlet.ServletHolder;
-import org.eclipse.jetty.util.thread.QueuedThreadPool;
-
-import javax.servlet.http.HttpServlet;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import java.util.function.BiConsumer;
-
-public class Http2TestServer {
-
-    private final String path;
-    private final Server server;
-    private final ServerConnector connector;
-
-    public static TestServerBuilder servlet(HttpServlet servlet) {
-        return new TestServerBuilder(servlet, "/", 0);
-    }
-
-    public static TestServerBuilder handler(BiConsumer<HttpServletRequest, HttpServletResponse> handler) {
-
-        HttpServlet servlet = new HttpServlet() {
-            private static final long serialVersionUID = -7741340028518626628L;
-
-            @Override
-            protected void service(HttpServletRequest req, HttpServletResponse resp) {
-                handler.accept(req, resp);
-            }
-        };
-
-        return servlet(servlet);
-    }
-
-
-    public Http2TestServer(HttpServlet servlet, String path, int port) {
-        this.path = path;
-
-        QueuedThreadPool serverExecutor = new QueuedThreadPool();
-        serverExecutor.setName("server");
-
-        server = new Server(serverExecutor);
-        connector = new ServerConnector(server, 1, 1, new HTTP2ServerConnectionFactory(new HttpConfiguration()));
-        connector.setPort(port);
-        server.addConnector(connector);
-
-        ServletContextHandler context = new ServletContextHandler(server, "/", true, false);
-        context.addServlet(new ServletHolder(servlet), path);
-    }
-
-    void start() {
-        try {
-            server.start();
-        } catch (Exception e) {
-            throw new RuntimeException(e);
-        }
-    }
-
-    public void stop() {
-        try {
-            server.stop();
-        } catch (Exception e) {
-            throw new RuntimeException(e);
-        }
-    }
-
-    public int getLocalPort() {
-        return connector.getLocalPort();
-    }
-
-
-    public String getBasePath() {
-        return "http://localhost:" + getLocalPort() + path;
-    }
-
-
-    public static class TestServerBuilder {
-        private final HttpServlet servlet;
-        private final String path;
-        private final int port;
-
-        private TestServerBuilder(HttpServlet servlet, String path, int port) {
-            this.servlet = servlet;
-            this.path = path;
-            this.port = port;
-        }
-
-        public TestServerBuilder path(String path) {
-            return new TestServerBuilder(this.servlet, path, this.port);
-        }
-
-        public TestServerBuilder port(int port) {
-            return new TestServerBuilder(this.servlet, this.path, port);
-        }
-
-
-        public Http2TestServer start() {
-            Http2TestServer http2Server = new Http2TestServer(servlet, path, port);
-            http2Server.start();
-            return http2Server;
-        }
-    }
-}
diff --git a/cayenne-client/pom.xml b/cayenne-client/pom.xml
deleted file mode 100644
index 08fdd6e13..000000000
--- a/cayenne-client/pom.xml
+++ /dev/null
@@ -1,135 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!-- Licensed to the Apache Software Foundation (ASF) under one or more contributor 
-	license agreements. See the NOTICE file distributed with this work for additional 
-	information regarding copyright ownership. The ASF licenses this file to 
-	you under the Apache License, Version 2.0 (the "License"); you may not use 
-	this file except in compliance with the License. You may obtain a copy of 
-	the License at https://www.apache.org/licenses/LICENSE-2.0 Unless required 
-	by applicable law or agreed to in writing, software distributed under the 
-	License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS 
-	OF ANY KIND, either express or implied. See the License for the specific 
-	language governing permissions and limitations under the License. -->
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
-	<modelVersion>4.0.0</modelVersion>
-	<parent>
-		<groupId>org.apache.cayenne</groupId>
-		<artifactId>cayenne-parent</artifactId>
-		<version>4.3.M1-SNAPSHOT</version>
-	</parent>
-	<artifactId>cayenne-client</artifactId>
-	<packaging>jar</packaging>
-	<name>cayenne-client: Cayenne ROP Client</name>
-	<dependencies>
-
-		<!-- Compile dependencies -->
-        <dependency>
-            <groupId>org.slf4j</groupId>
-            <artifactId>slf4j-api</artifactId>
-            <scope>compile</scope>
-        </dependency>
-		<dependency>
-			<groupId>org.apache.cayenne</groupId>
-			<artifactId>cayenne-di</artifactId>
-			<version>${project.version}</version>
-			<scope>compile</scope>
-		</dependency>
-		<dependency>
-			<groupId>org.apache.cayenne</groupId>
-			<artifactId>cayenne-server</artifactId>
-			<version>${project.version}</version>
-			<scope>compile</scope>
-		</dependency>
-		<dependency>
-			<groupId>com.caucho</groupId>
-            <artifactId>hessian</artifactId>
-			<scope>compile</scope>
-		</dependency>
-        <dependency>
-            <groupId>org.apache.cayenne</groupId>
-            <artifactId>cayenne-rop-server</artifactId>
-            <version>${project.version}</version>
-        </dependency>
-
-		<!-- Test dependencies -->
-		<dependency>
-			<groupId>junit</groupId>
-			<artifactId>junit</artifactId>
-			<scope>test</scope>
-		</dependency>
-		<dependency>
-			<groupId>org.mockito</groupId>
-			<artifactId>mockito-core</artifactId>
-			<scope>test</scope>
-		</dependency>
-		<dependency>
-			<groupId>org.apache.cayenne.build-tools</groupId>
-			<artifactId>cayenne-test-utilities</artifactId>
-			<version>${project.version}</version>
-			<scope>test</scope>
-		</dependency>
-		<dependency>
-			<groupId>org.apache.cayenne</groupId>
-			<artifactId>cayenne-server</artifactId>
-			<version>${project.version}</version>
-			<type>test-jar</type>
-			<scope>test</scope>
-		</dependency>
-		<dependency>
-    		<groupId>org.slf4j</groupId>
-    		<artifactId>slf4j-simple</artifactId>
-    		<scope>test</scope>
-		</dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>testcontainers</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>mysql</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>mariadb</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>postgresql</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>oracle-xe</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>mssqlserver</artifactId>
-            <scope>test</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.testcontainers</groupId>
-            <artifactId>db2</artifactId>
-            <scope>test</scope>
-        </dependency>
-    </dependencies>
-
-	<build>
-		<plugins>
-			<!-- This ensures LICENSE and NOTICE inclusion in all jars -->
-            <plugin>
-                <artifactId>maven-remote-resources-plugin</artifactId>
-                <executions>
-                    <execution>
-                        <goals>
-                            <goal>process</goal>
-                        </goals>
-                    </execution>
-                </executions>
-            </plugin>
-        </plugins>
-    </build>
-
-</project>
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/CayenneClientModuleProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/CayenneClientModuleProvider.java
deleted file mode 100644
index b01dfa656..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/CayenneClientModuleProvider.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.di.spi.ModuleProvider;
-
-/**
- * This interface implementations will be used by {@link ClientRuntimeBuilder} to auto-load client modules.
- * @since 4.0
- */
-public interface CayenneClientModuleProvider extends ModuleProvider {
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/CayenneContextFactory.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/CayenneContextFactory.java
deleted file mode 100644
index e8e8d05f2..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/CayenneContextFactory.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.CayenneContext;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.ObjectContext;
-import org.apache.cayenne.cache.NestedQueryCache;
-import org.apache.cayenne.cache.QueryCache;
-import org.apache.cayenne.configuration.Constants;
-import org.apache.cayenne.configuration.ObjectContextFactory;
-import org.apache.cayenne.configuration.RuntimeProperties;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.di.Injector;
-
-public class CayenneContextFactory implements ObjectContextFactory {
-
-    @Inject
-    protected DataChannel dataChannel;
-
-    @Inject
-    protected RuntimeProperties properties;
-    
-    @Inject
-    protected QueryCache queryCache;
-
-    @Inject
-    protected Injector injector;
-
-    public ObjectContext createContext() {
-        return createContext(dataChannel);
-    }
-
-    public ObjectContext createContext(DataChannel parent) {
-        boolean changeEvents = properties.getBoolean(
-                ClientConstants.ROP_CONTEXT_CHANGE_EVENTS_PROPERTY,
-                false);
-
-        boolean lifecycleEvents = properties.getBoolean(
-                ClientConstants.ROP_CONTEXT_LIFECYCLE_EVENTS_PROPERTY,
-                false);
-
-        CayenneContext context = newInstance(parent, changeEvents, lifecycleEvents);
-        context.setQueryCache(new NestedQueryCache(queryCache));
-        return context;
-    }
-    
-    protected CayenneContext newInstance(DataChannel parent, boolean changeEventsEnabled, boolean lifecycleEventsEnabled) {
-        return new CayenneContext(parent, changeEventsEnabled, lifecycleEventsEnabled);
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientChannelProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientChannelProvider.java
deleted file mode 100644
index 1ea7e5b11..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientChannelProvider.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.ConfigurationException;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.configuration.RuntimeProperties;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.event.EventManager;
-import org.apache.cayenne.remote.ClientChannel;
-import org.apache.cayenne.remote.ClientConnection;
-
-public class ClientChannelProvider implements Provider<DataChannel> {
-
-    @Inject
-    protected ClientConnection connection;
-
-    @Inject
-    protected EventManager eventManager;
-
-    @Inject
-    protected RuntimeProperties properties;
-
-    public DataChannel get() throws ConfigurationException {
-
-        boolean channelEvents = properties.getBoolean(ClientConstants.ROP_CHANNEL_EVENTS_PROPERTY, false);
-
-        return new ClientChannel(connection, channelEvents, eventManager, channelEvents);
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientConstants.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientConstants.java
deleted file mode 100644
index 69e024e7e..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientConstants.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- *    Licensed to the Apache Software Foundation (ASF) under one
- *    or more contributor license agreements.  See the NOTICE file
- *    distributed with this work for additional information
- *    regarding copyright ownership.  The ASF licenses this file
- *    to you under the Apache License, Version 2.0 (the
- *    "License"); you may not use this file except in compliance
- *    with the License.  You may obtain a copy of the License at
- *
- *      https://www.apache.org/licenses/LICENSE-2.0
- *
- *    Unless required by applicable law or agreed to in writing,
- *    software distributed under the License is distributed on an
- *    "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *    KIND, either express or implied.  See the License for the
- *    specific language governing permissions and limitations
- *    under the License.
- */
-package org.apache.cayenne.configuration.rop.client;
-
-/**
- * Defines the names of runtime properties and named collections used in DI modules related to ROP client.
- *
- * @since 4.0
- */
-public class ClientConstants {
-
-    public static final String ROP_SERVICE_URL_PROPERTY = "cayenne.rop.service_url";
-
-    public static final String ROP_SERVICE_USERNAME_PROPERTY = "cayenne.rop.service_username";
-
-    public static final String ROP_SERVICE_PASSWORD_PROPERTY = "cayenne.rop.service_password";
-
-    public static final String ROP_SERVICE_REALM_PROPERTY = "cayenne.rop.service_realm";
-
-    /**
-     * A boolean property that defines whether ALPN should be used. Possible values are "true" or "false".
-     */
-    public static final String ROP_SERVICE_USE_ALPN_PROPERTY = "cayenne.rop.service_use_alpn";
-
-    public static final String ROP_SERVICE_SHARED_SESSION_PROPERTY = "cayenne.rop.shared_session_name";
-
-    public static final String ROP_SERVICE_TIMEOUT_PROPERTY = "cayenne.rop.service_timeout";
-
-    public static final String ROP_CHANNEL_EVENTS_PROPERTY = "cayenne.rop.channel_events";
-
-    public static final String ROP_CONTEXT_CHANGE_EVENTS_PROPERTY = "cayenne.rop.context_change_events";
-
-    public static final String ROP_CONTEXT_LIFECYCLE_EVENTS_PROPERTY = "cayenne.rop.context_lifecycle_events";
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientModule.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientModule.java
deleted file mode 100644
index ade6f722d..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientModule.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.cache.MapQueryCacheProvider;
-import org.apache.cayenne.cache.QueryCache;
-import org.apache.cayenne.configuration.DefaultRuntimeProperties;
-import org.apache.cayenne.configuration.ObjectContextFactory;
-import org.apache.cayenne.configuration.RuntimeProperties;
-import org.apache.cayenne.configuration.server.ServerModule;
-import org.apache.cayenne.di.Binder;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.event.EventManager;
-import org.apache.cayenne.event.EventManagerProvider;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.RemoteService;
-import org.apache.cayenne.rop.HttpClientConnectionProvider;
-import org.apache.cayenne.rop.ProxyRemoteService;
-import org.apache.cayenne.rop.ROPSerializationService;
-import org.apache.cayenne.rop.http.ClientHessianSerializationServiceProvider;
-
-/**
- * A DI module containing all Cayenne ROP client runtime configurations.
- * 
- * @since 3.1
- * @since 4.0 this module is auto-loaded by {@link ClientRuntimeBuilder}
- */
-public class ClientModule implements Module {
-
-    /**
-     * @since 4.0
-     */
-    public ClientModule() {
-    }
-
-    @SuppressWarnings("deprecation")
-    public void configure(Binder binder) {
-
-        // Contribute always to create binding
-        ServerModule.contributeProperties(binder);
-
-        binder.bind(ObjectContextFactory.class).to(CayenneContextFactory.class);
-        binder.bind(ROPSerializationService.class).toProvider(ClientHessianSerializationServiceProvider.class);
-        binder.bind(RemoteService.class).to(ProxyRemoteService.class);
-        binder.bind(ClientConnection.class).toProvider(HttpClientConnectionProvider.class);
-        binder.bind(EventManager.class).toProvider(EventManagerProvider.class);
-        binder.bind(RuntimeProperties.class).to(DefaultRuntimeProperties.class);
-        binder.bind(DataChannel.class).toProvider(ClientChannelProvider.class);
-        binder.bind(QueryCache.class).toProvider(MapQueryCacheProvider.class);
-    }
-
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientRuntime.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientRuntime.java
deleted file mode 100644
index b59673feb..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientRuntime.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.configuration.CayenneRuntime;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.remote.ClientConnection;
-
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Map;
-
-import static java.util.Arrays.asList;
-
-/**
- * A user application entry point to Cayenne stack on the ROP client.
- * 
- * @since 3.1
- * @since 4.0 preferred way to create this class is with {@link ClientRuntime#builder()} method.
- */
-public class ClientRuntime extends CayenneRuntime {
-
-	/**
-	 * @since 4.0 moved from deprecated ClientLocalRuntime class
-	 */
-	public static final String CLIENT_SERVER_CHANNEL_KEY = "client-server-channel";
-
-	/**
-	 * Creates new builder of client runtime
-	 * @return client runtime builder
-	 *
-	 * @since 4.0
-	 */
-	public static ClientRuntimeBuilder builder() {
-		return new ClientRuntimeBuilder();
-	}
-
-	/**
-	 * @since 4.0
-	 */
-	protected ClientRuntime(Collection<Module> modules) {
-		super(modules);
-	}
-
-	public ClientConnection getConnection() {
-		return injector.getInstance(ClientConnection.class);
-	}
-
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeBuilder.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeBuilder.java
deleted file mode 100644
index caf6def2e..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeBuilder.java
+++ /dev/null
@@ -1,147 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.configuration.server.ServerModule;
-import org.apache.cayenne.di.Injector;
-import org.apache.cayenne.di.Key;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.di.spi.ModuleLoader;
-import org.apache.cayenne.remote.ClientConnection;
-
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.List;
-import java.util.Map;
-
-
-/**
- * <p>
- * A convenience class to assemble custom ClientRuntime.
- * It allows to easily configure custom modules and create local runtime.
- * </p>
- * <p>
- * To create this builder use {@link ClientRuntime#builder()} method.
- * </p>
- *
- * @since 4.0
- */
-public class ClientRuntimeBuilder {
-
-    private List<Module> modules;
-    private boolean autoLoadModules;
-    private boolean local;
-    Injector serverInjector;
-    private Map<String, String> properties;
-
-    ClientRuntimeBuilder() {
-        modules = new ArrayList<>();
-        autoLoadModules = true;
-        local = false;
-        properties = null;
-    }
-
-    /**
-     * Disables DI module auto-loading. By default auto-loading is enabled based on
-     * {@link CayenneClientModuleProvider} service provider interface.
-     * If you decide to disable auto-loading, make sure you provide all the modules that you need.
-     *
-     * @return this builder instance.
-     */
-    public ClientRuntimeBuilder disableModulesAutoLoading() {
-        this.autoLoadModules = false;
-        return this;
-    }
-
-    public ClientRuntimeBuilder addModule(Module module) {
-        modules.add(module);
-        return this;
-    }
-
-    public ClientRuntimeBuilder addModules(Collection<Module> modules) {
-        this.modules.addAll(modules);
-        return this;
-    }
-
-    /**
-     * @param properties contributed to {@link ServerModule}
-     * @return this builder
-     */
-    public ClientRuntimeBuilder properties(Map<String, String> properties) {
-        this.properties = properties;
-        return this;
-    }
-
-    /**
-     * Create {@link ClientRuntime} that provides an ROP stack based on a local
-     * connection on top of a server stack.
-     *
-     * @param serverInjector server injector
-     * @return this builder
-     */
-    public ClientRuntimeBuilder local(Injector serverInjector) {
-        this.local = true;
-        this.serverInjector = serverInjector;
-        return this;
-    }
-
-    public ClientRuntime build() {
-        Collection<Module> allModules = new ArrayList<>();
-
-        // first load default or auto-loaded modules...
-        allModules.addAll(autoLoadModules ? autoLoadedModules() : defaultModules());
-
-        // custom modules override default and auto-loaded ...
-        allModules.addAll(modules);
-
-        // builder modules override default, auto-loaded and custom modules...
-        allModules.addAll(builderModules());
-
-        return new ClientRuntime(allModules);
-    }
-
-    private Collection<? extends Module> autoLoadedModules() {
-        return new ModuleLoader().load(CayenneClientModuleProvider.class);
-    }
-
-    private Collection<? extends Module> defaultModules() {
-        return Collections.singleton(new ClientModule());
-    }
-
-    private Collection<? extends Module> builderModules() {
-        Collection<Module> modules = new ArrayList<>();
-
-        if(properties != null) {
-            modules.add(binder -> ServerModule.contributeProperties(binder).putAll(properties));
-        }
-
-        if(local) {
-            modules.add(binder -> {
-                binder.bind(Key.get(DataChannel.class, ClientRuntime.CLIENT_SERVER_CHANNEL_KEY))
-                        .toProviderInstance(new LocalClientServerChannelProvider(serverInjector));
-                binder.bind(ClientConnection.class).toProviderInstance(new LocalConnectionProvider());
-            });
-        }
-
-        return modules;
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/LocalClientServerChannelProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/LocalClientServerChannelProvider.java
deleted file mode 100644
index d7ece3821..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/LocalClientServerChannelProvider.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.ConfigurationException;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.access.ClientServerChannel;
-import org.apache.cayenne.access.DataContext;
-import org.apache.cayenne.configuration.ObjectContextFactory;
-import org.apache.cayenne.di.Injector;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.remote.service.LocalConnection;
-
-/**
- * Creates a {@link ClientServerChannel} for the {@link LocalConnection}.
- * 
- * @since 3.1
- */
-public class LocalClientServerChannelProvider implements Provider<DataChannel> {
-
-    protected Injector serverInjector;
-
-    public LocalClientServerChannelProvider(Injector serverInjector) {
-        this.serverInjector = serverInjector;
-    }
-
-    public DataChannel get() throws ConfigurationException {
-        ObjectContextFactory factory = serverInjector
-                .getInstance(ObjectContextFactory.class);
-
-        // TODO: ugly cast
-        DataContext serverContext = (DataContext) factory.createContext();
-        return new ClientServerChannel(serverContext);
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/LocalConnectionProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/LocalConnectionProvider.java
deleted file mode 100644
index e9ccc1cb5..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/LocalConnectionProvider.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.ConfigurationException;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.service.LocalConnection;
-
-/**
- * @since 3.1
- */
-public class LocalConnectionProvider implements Provider<ClientConnection> {
-
-    @Inject(ClientRuntime.CLIENT_SERVER_CHANNEL_KEY)
-    protected Provider<DataChannel> clientServerChannelProvider;
-
-    public ClientConnection get() throws ConfigurationException {
-
-        DataChannel clientServerChannel = clientServerChannelProvider.get();
-        return new LocalConnection(
-                clientServerChannel,
-                LocalConnection.HESSIAN_SERIALIZATION);
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/MainCayenneClientModuleProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/MainCayenneClientModuleProvider.java
deleted file mode 100644
index 95b5d000a..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/configuration/rop/client/MainCayenneClientModuleProvider.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import java.util.Collection;
-import java.util.Collections;
-
-import org.apache.cayenne.di.Module;
-
-/**
- * @since 4.0
- */
-public class MainCayenneClientModuleProvider implements CayenneClientModuleProvider {
-
-    @Override
-    public Module module() {
-        return new ClientModule();
-    }
-
-    @Override
-    public Class<? extends Module> moduleType() {
-        return ClientModule.class;
-    }
-
-    @Override
-    public Collection<Class<? extends Module>> overrides() {
-        return Collections.emptyList();
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/BaseConnection.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/BaseConnection.java
deleted file mode 100644
index 47d9ba491..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/BaseConnection.java
+++ /dev/null
@@ -1,125 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote;
-
-import org.slf4j.Logger;
-import org.apache.cayenne.CayenneRuntimeException;
-import org.slf4j.LoggerFactory;
-
-/**
- * A common base class for concrete ClientConnection implementations. Provides message
- * logging functionality via slf4j logging.
- * 
- * @since 1.2
- */
-public abstract class BaseConnection implements ClientConnection {
-
-    protected Logger logger;
-    protected long messageId;
-    
-    /**
-     * Default constructor that initializes logging and a single threaded EventManager.
-     */
-    protected BaseConnection() {
-        this.logger = LoggerFactory.getLogger(getClass());
-    }
-
-    /**
-     * Invokes 'beforeSendMessage' on self, then invokes 'doSendMessage'. Implements basic
-     * logging functionality. Do not override this method unless absolutely necessary.
-     * Override 'beforeSendMessage' and 'doSendMessage' instead.
-     */
-    public Object sendMessage(ClientMessage message) throws CayenneRuntimeException {
-        if (message == null) {
-            throw new NullPointerException("Null message");
-        }
-
-        beforeSendMessage(message);
-
-        // log start...
-        long t0 = 0;
-        String messageLabel = "";
-
-        // using sequential number for message id ... it can be useful for some basic
-        // connector stats.
-        long messageId = this.messageId++;
-
-        if (logger.isInfoEnabled()) {
-            t0 = System.currentTimeMillis();
-            messageLabel = message.toString();
-            logger.info("--- Message " + messageId + ": " + messageLabel);
-        }
-
-        Object response;
-        try {
-            response = doSendMessage(message);
-        }
-        catch (CayenneRuntimeException e) {
-
-            // log error
-            if (logger.isInfoEnabled()) {
-                long time = System.currentTimeMillis() - t0;
-                logger.info("*** Message error for "
-                        + messageId
-                        + ": "
-                        + messageLabel
-                        + " - took "
-                        + time
-                        + " ms.");
-            }
-
-            throw e;
-        }
-
-        // log success...
-        if (logger.isInfoEnabled()) {
-            long time = System.currentTimeMillis() - t0;
-            logger.info("=== Message "
-                    + messageId
-                    + ": "
-                    + messageLabel
-                    + " done - took "
-                    + time
-                    + " ms.");
-        }
-
-        return response;
-    }
-
-    /**
-     * Returns a count of processed messages since the beginning of life of this
-     * connector.
-     */
-    public long getProcessedMessagesCount() {
-        return messageId + 1;
-    }
-    
-    /**
-     * Called before logging the beginning of message processing.
-     */
-    protected abstract void beforeSendMessage(ClientMessage message)
-            throws CayenneRuntimeException;
-
-    /**
-     * The worker method invoked to process message.
-     */
-    protected abstract Object doSendMessage(ClientMessage message)
-            throws CayenneRuntimeException;
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/ClientChannel.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/ClientChannel.java
deleted file mode 100644
index e7cff78a4..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/ClientChannel.java
+++ /dev/null
@@ -1,314 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.DataChannelSyncCallbackAction;
-import org.apache.cayenne.ObjectContext;
-import org.apache.cayenne.ObjectId;
-import org.apache.cayenne.Persistent;
-import org.apache.cayenne.QueryResponse;
-import org.apache.cayenne.event.EventBridge;
-import org.apache.cayenne.event.EventManager;
-import org.apache.cayenne.event.EventSubject;
-import org.apache.cayenne.graph.CompoundDiff;
-import org.apache.cayenne.graph.GraphDiff;
-import org.apache.cayenne.graph.GraphDiffCompressor;
-import org.apache.cayenne.graph.GraphEvent;
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.query.EntityResultSegment;
-import org.apache.cayenne.query.Query;
-import org.apache.cayenne.query.QueryMetadata;
-import org.apache.cayenne.util.DeepMergeOperation;
-import org.apache.cayenne.util.ToStringBuilder;
-
-import java.util.List;
-import java.util.ListIterator;
-
-/**
- * A {@link org.apache.cayenne.DataChannel} implementation that accesses a remote server
- * via a ClientConnection.
- * 
- * @since 1.2
- */
-public class ClientChannel implements DataChannel {
-
-    protected ClientConnection connection;
-    protected EventManager eventManager;
-    protected EntityResolver entityResolver;
-    protected boolean channelEventsEnabled;
-    protected GraphDiffCompressor diffCompressor;
-
-    EventBridge remoteChannelListener;
-
-    /**
-     * @param remoteEventsOptional if true, failure to start an EventBridge will not
-     *            result in an exception.
-     * @since 3.0
-     */
-    public ClientChannel(ClientConnection connection, boolean channelEventsEnabled,
-            EventManager eventManager, boolean remoteEventsOptional)
-            throws CayenneRuntimeException {
-
-        this.connection = connection;
-        this.diffCompressor = new GraphDiffCompressor();
-        this.eventManager = eventManager;
-        this.channelEventsEnabled = eventManager != null && channelEventsEnabled;
-
-        if (!remoteEventsOptional) {
-            setupRemoteChannelListener();
-        } else {
-            try {
-                setupRemoteChannelListener();
-            } catch (CayenneRuntimeException ignored) {}
-        }
-    }
-
-    /**
-     * @since 3.1
-     */
-    public ClientConnection getConnection() {
-        return connection;
-    }
-
-    /**
-     * @since 3.1
-     */
-    public boolean isChannelEventsEnabled() {
-        return channelEventsEnabled;
-    }
-
-    public EventManager getEventManager() {
-        return eventManager;
-    }
-
-    @SuppressWarnings("unchecked")
-    public QueryResponse onQuery(ObjectContext context, Query query) {
-
-        QueryResponse response = send( new QueryMessage(query), QueryResponse.class);
-
-        // if needed, register objects in provided context, rewriting the response
-        // (assuming all lists are mutable)
-
-        if (context != null) {
-
-            EntityResolver resolver = context.getEntityResolver();
-            QueryMetadata info = query.getMetaData(resolver);
-
-            if (!info.isFetchingDataRows()) {
-
-                response.reset();
-
-                while (response.next()) {
-                    if (response.isList()) {
-
-                        List objects = response.currentList();
-
-                        if (!objects.isEmpty()) {
-
-                            DeepMergeOperation merger = new DeepMergeOperation(context);
-                            List<Object> rsMapping = info.getResultSetMapping();
-                            if (rsMapping == null) {
-                                convertSingleObjects(objects, merger);
-                            }
-                            else {
-                                if (rsMapping.size() == 1) {
-                                    if (rsMapping.get(0) instanceof EntityResultSegment) {
-                                        convertSingleObjects(objects, merger);
-                                    }
-                                }
-                                else {
-                                    processMixedResult(objects, merger, rsMapping);
-                                }
-                            }
-                        }
-                    }
-                }
-            }
-        }
-
-        return response;
-    }
-
-    private void processMixedResult(
-            List<Object[]> objects,
-            DeepMergeOperation merger,
-            List<Object> rsMapping) {
-
-        int width = rsMapping.size();
-        for (int i = 0; i < width; i++) {
-            if (rsMapping.get(i) instanceof EntityResultSegment) {
-                for (Object[] object : objects) {
-                    object[i] = convertObject(merger, (Persistent) object[i]);
-                }
-            }
-        }
-    }
-
-    private void convertSingleObjects(List<Object> objects, DeepMergeOperation merger) {
-
-        ListIterator<Object> it = objects.listIterator();
-        while (it.hasNext()) {
-            Object next = it.next();
-            it.set(convertObject( merger, (Persistent) next));
-        }
-    }
-
-    private Object convertObject(DeepMergeOperation merger, Persistent object) {
-
-        ObjectId id = object.getObjectId();
-
-        // sanity check
-        if (id == null) {
-            throw new CayenneRuntimeException("Server returned an object without an id: %s", object);
-        }
-
-        return merger.merge(object);
-    }
-
-    public GraphDiff onSync(
-            ObjectContext originatingContext,
-            GraphDiff changes,
-            int syncType) {
-
-        DataChannelSyncCallbackAction callbackAction = DataChannelSyncCallbackAction
-                .getCallbackAction(
-                        getEntityResolver().getCallbackRegistry(),
-                        originatingContext.getGraphManager(),
-                        changes,
-                        syncType);
-        callbackAction.applyPreCommit();
-
-        changes = diffCompressor.compress(changes);
-
-        GraphDiff replyDiff = send(new SyncMessage(
-                originatingContext,
-                syncType,
-                changes), GraphDiff.class);
-
-        if (channelEventsEnabled) {
-            EventSubject subject;
-
-            switch (syncType) {
-                case DataChannel.ROLLBACK_CASCADE_SYNC:
-                    subject = DataChannel.GRAPH_ROLLEDBACK_SUBJECT;
-                    break;
-                case DataChannel.FLUSH_NOCASCADE_SYNC:
-                    subject = DataChannel.GRAPH_CHANGED_SUBJECT;
-                    break;
-                case DataChannel.FLUSH_CASCADE_SYNC:
-                    subject = DataChannel.GRAPH_FLUSHED_SUBJECT;
-                    break;
-                default:
-                    subject = null;
-            }
-
-            if (subject != null) {
-
-                // combine message sender changes and message receiver changes into a
-                // single event
-                boolean sentNoop = changes == null || changes.isNoop();
-                boolean receivedNoop = replyDiff == null || replyDiff.isNoop();
-
-                if (!sentNoop || !receivedNoop) {
-                    CompoundDiff notification = new CompoundDiff();
-
-                    if (!sentNoop) {
-                        notification.add(changes);
-                    }
-
-                    if (!receivedNoop) {
-                        notification.add(replyDiff);
-                    }
-
-                    GraphEvent e = new GraphEvent(this, originatingContext, notification);
-                    eventManager.postEvent(e, subject);
-                }
-            }
-        }
-
-        callbackAction.applyPostCommit();
-        return replyDiff;
-    }
-
-    /**
-     * Returns EntityResolver obtained from the server. On first access, this method sends
-     * a message to the server to retrieve the EntityResolver. On subsequent calls locally
-     * cached resolver is used.
-     */
-    public EntityResolver getEntityResolver() {
-        if (entityResolver == null) {
-            synchronized (this) {
-                if (entityResolver == null) {
-                    entityResolver = send(new BootstrapMessage(), EntityResolver.class);
-                }
-            }
-        }
-
-        return entityResolver;
-    }
-
-    /**
-     * Starts up an EventBridge to listen for remote updates. Returns true if the listener
-     * was setup, false if not. False can be returned if the underlying connection doesn't
-     * support events of if there is no EventManager available.
-     */
-    protected boolean setupRemoteChannelListener() throws CayenneRuntimeException {
-        if (eventManager == null) {
-            return false;
-        }
-
-        EventBridge bridge = connection.getServerEventBridge();
-        if (bridge == null) {
-            return false;
-        }
-
-        try {
-            // make sure events are sent on behalf of this channel...and received from all
-            bridge.startup(eventManager, EventBridge.RECEIVE_LOCAL_EXTERNAL, null, this);
-        }
-        catch (Exception e) {
-            throw new CayenneRuntimeException("Error starting EventBridge " + bridge, e);
-        }
-
-        this.remoteChannelListener = bridge;
-        return true;
-    }
-
-    /**
-     * Sends a message via connector, getting a result as an instance of a specific class.
-     * 
-     * @throws org.apache.cayenne.CayenneRuntimeException if an underlying connector
-     *             exception occurred, or a result is not of expected type.
-     */
-    protected <T> T send(ClientMessage message, Class<T> resultClass) {
-        Object result = connection.sendMessage(message);
-
-        if (result != null && !resultClass.isInstance(result)) {
-            String resultString = new ToStringBuilder(result).toString();
-            throw new CayenneRuntimeException("Expected result type: %s, actual: %s"
-                    , resultClass.getName()
-                    , resultString);
-        }
-
-        return resultClass.cast(result);
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/ClientConnection.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/ClientConnection.java
deleted file mode 100644
index 4233febc3..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/ClientConnection.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.event.EventBridge;
-
-/**
- * A connection object used to interact with a remote Cayenne server. Connection supports
- * synchronous interaction via {@link #sendMessage(ClientMessage)} and asynchronous
- * listening for server events.
- * 
- * @since 1.2
- */
-public interface ClientConnection {
-
-    /**
-     * Returns an EventBridge that receives remote server events. Caller would normally
-     * register returned bridge with a local EventManager, thus allowing local listeners
-     * to receive server events.
-     * 
-     * @return An EventBridge or null if server events are not supported.
-     */
-    EventBridge getServerEventBridge() throws CayenneRuntimeException;
-
-    /**
-     * Sends a synchronous ClientMessage to the server, returning a reply.
-     */
-    Object sendMessage(ClientMessage message) throws CayenneRuntimeException;
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/ClientSerializerFactory.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/ClientSerializerFactory.java
deleted file mode 100644
index 02212e87c..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/ClientSerializerFactory.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote.hessian;
-
-import com.caucho.hessian.io.FieldDeserializer2Factory;
-import org.apache.cayenne.DataRow;
-import org.apache.cayenne.util.PersistentObjectList;
-import org.apache.cayenne.util.PersistentObjectMap;
-
-import com.caucho.hessian.io.AbstractSerializerFactory;
-import com.caucho.hessian.io.Deserializer;
-import com.caucho.hessian.io.JavaDeserializer;
-import com.caucho.hessian.io.Serializer;
-
-/**
- * An object that manages all custom (de)serializers used on the client.
- * 
- * @since 1.2
- */
-public class ClientSerializerFactory extends AbstractSerializerFactory {
-
-    private Deserializer dataRowDeserializer;
-    private Deserializer listDeserializer;
-    private Deserializer mapDeserializer;
-
-    @Override
-    public Serializer getSerializer(Class cl) {
-        return null;
-    }
-
-    @Override
-    public Deserializer getDeserializer(Class cl) {
-        //turns out Hessian uses its own (incorrect) serialization mechanism for maps
-        if (PersistentObjectMap.class.isAssignableFrom(cl)) {
-            if (mapDeserializer == null) {
-                mapDeserializer = new JavaDeserializer(cl, FieldDeserializer2Factory.create());
-            }
-            return mapDeserializer;
-        }
-        
-        if (PersistentObjectList.class.isAssignableFrom(cl)) {
-            if (listDeserializer == null) {
-                listDeserializer = new JavaDeserializer(cl, FieldDeserializer2Factory.create());
-            }
-            return listDeserializer;
-        }
-        
-        if(DataRow.class.isAssignableFrom(cl)) {
-            if(dataRowDeserializer == null) {
-                dataRowDeserializer = new DataRowDeserializer();
-            }
-            
-            return dataRowDeserializer;
-        }
-
-        return null;
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/DataRowDeserializer.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/DataRowDeserializer.java
deleted file mode 100644
index 2c0a381c5..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/DataRowDeserializer.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote.hessian;
-
-import java.io.IOException;
-import java.lang.reflect.Field;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.DataRow;
-
-import com.caucho.hessian.io.AbstractHessianInput;
-import com.caucho.hessian.io.AbstractMapDeserializer;
-
-/**
- * Client side deserilaizer of DataRows.
- * 
- * @since 1.2
- */
-class DataRowDeserializer extends AbstractMapDeserializer {
-
-    protected Field versionField;
-
-    DataRowDeserializer() {
-        try {
-            versionField = DataRow.class.getDeclaredField("version");
-        }
-        catch (Exception e) {
-            throw new CayenneRuntimeException(
-                    "Error building deserializer for DataRow",
-                    e);
-        }
-
-        versionField.setAccessible(true);
-    }
-
-    @Override
-    public Class<?> getType() {
-        return DataRow.class;
-    }
-
-    @Override
-    public Object readMap(AbstractHessianInput in) throws IOException {
-
-        int size = in.readInt();
-        DataRow row = new DataRow(size);
-        try {
-            versionField.set(row, Long.valueOf(in.readLong()));
-        }
-        catch (Exception e) {
-            throw new IOException("Error reading 'version' field");
-        }
-
-        row.setReplacesVersion(in.readLong());
-        in.addRef(row);
-
-        while (!in.isEnd()) {
-            row.put((String) in.readObject(), in.readObject());
-        }
-
-        in.readEnd();
-
-        return row;
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/service/HessianUtil.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/service/HessianUtil.java
deleted file mode 100644
index b16dce91b..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/hessian/service/HessianUtil.java
+++ /dev/null
@@ -1,87 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote.hessian.service;
-
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.Serializable;
-
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.HessianConfig;
-
-import com.caucho.hessian.io.HessianInput;
-import com.caucho.hessian.io.HessianOutput;
-import org.apache.cayenne.rop.ServerHessianSerializationServiceProvider;
-import org.apache.cayenne.rop.http.ClientHessianSerializationServiceProvider;
-
-/**
- * Hessian related utilities.
- * 
- * @since 1.2
- */
-public class HessianUtil {
-
-    /**
-     * A utility method that clones an object using Hessian serialization/deserialization
-     * mechanism, which is different from default Java serialization.
-     */
-    public static Object cloneViaClientServerSerialization(
-            Serializable object,
-            EntityResolver serverResolver) throws Exception {
-        ByteArrayOutputStream bytes = new ByteArrayOutputStream();
-        HessianOutput out = new HessianOutput(bytes);
-        out.setSerializerFactory(HessianConfig.createFactory(
-                ClientHessianSerializationServiceProvider.CLIENT_SERIALIZER_FACTORIES,
-                null));
-        out.writeObject(object);
-
-        byte[] data = bytes.toByteArray();
-
-        HessianInput in = new HessianInput(new ByteArrayInputStream(data));
-        in.setSerializerFactory(HessianConfig.createFactory(
-                ServerHessianSerializationServiceProvider.SERVER_SERIALIZER_FACTORIES,
-                serverResolver));
-
-        return in.readObject();
-    }
-
-    public static Object cloneViaServerClientSerialization(
-            Serializable object,
-            EntityResolver serverResolver) throws Exception {
-        ByteArrayOutputStream bytes = new ByteArrayOutputStream();
-        HessianOutput out = new HessianOutput(bytes);
-        out.setSerializerFactory(HessianConfig.createFactory(
-				ServerHessianSerializationServiceProvider.SERVER_SERIALIZER_FACTORIES,
-                serverResolver));
-        out.writeObject(object);
-
-        byte[] data = bytes.toByteArray();
-
-        HessianInput in = new HessianInput(new ByteArrayInputStream(data));
-        in.setSerializerFactory(HessianConfig.createFactory(
-                ClientHessianSerializationServiceProvider.CLIENT_SERIALIZER_FACTORIES,
-                null));
-        return in.readObject();
-    }
-
-    private HessianUtil() {
-
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/package.html b/cayenne-client/src/main/java/org/apache/cayenne/remote/package.html
deleted file mode 100644
index 1a3f7e660..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/package.html
+++ /dev/null
@@ -1,24 +0,0 @@
-<!--
-   Licensed to the Apache Software Foundation (ASF) under one
-   or more contributor license agreements.  See the NOTICE file
-   distributed with this work for additional information
-   regarding copyright ownership.  The ASF licenses this file
-   to you under the Apache License, Version 2.0 (the
-   "License"); you may not use this file except in compliance
-   with the License.  You may obtain a copy of the License at
-
-     https://www.apache.org/licenses/LICENSE-2.0
-
-   Unless required by applicable law or agreed to in writing,
-   software distributed under the License is distributed on an
-   "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-   KIND, either express or implied.  See the License for the
-   specific language governing permissions and limitations
-   under the License.
--->
-<html>
-	<body> Contains classes an interfaces related to Cayenne remote object persistence features. 
-Defines a set of message classes used for communication between client and server and provides a ClientChannel -
-a DataChannel implementation that connects to a remote service.
-	</body>
-</html>
\ No newline at end of file
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/remote/service/LocalConnection.java b/cayenne-client/src/main/java/org/apache/cayenne/remote/service/LocalConnection.java
deleted file mode 100644
index 520f55927..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/remote/service/LocalConnection.java
+++ /dev/null
@@ -1,144 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.remote.service;
-
-import java.io.Serializable;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.event.EventBridge;
-import org.apache.cayenne.remote.BaseConnection;
-import org.apache.cayenne.remote.ClientMessage;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.apache.cayenne.util.Util;
-
-/**
- * A ClientConnection that connects to a DataChannel. Used as an emulator of a remote
- * service. Emulation includes serialization/deserialization of objects.
- * 
- * @since 1.2
- */
-public class LocalConnection extends BaseConnection {
-
-    public static final int NO_SERIALIZATION = 0;
-    public static final int JAVA_SERIALIZATION = 1;
-    public static final int HESSIAN_SERIALIZATION = 2;
-
-    protected DataChannel channel;
-    protected int serializationPolicy;
-
-    /**
-     * Creates LocalConnector with specified handler and no serialization.
-     */
-    public LocalConnection(DataChannel handler) {
-        this(handler, NO_SERIALIZATION);
-    }
-
-    /**
-     * Creates a LocalConnector with specified handler and serialization policy. Valid
-     * policies are defined as final static int field in this class.
-     */
-    public LocalConnection(DataChannel handler, int serializationPolicy) {
-        this.channel = handler;
-
-        // convert invalid policy to NO_SER..
-        this.serializationPolicy = serializationPolicy == JAVA_SERIALIZATION
-                || serializationPolicy == HESSIAN_SERIALIZATION
-                ? serializationPolicy
-                : NO_SERIALIZATION;
-    }
-
-    public boolean isSerializingMessages() {
-        return serializationPolicy == JAVA_SERIALIZATION
-                || serializationPolicy == HESSIAN_SERIALIZATION;
-    }
-
-    /**
-     * Returns wrapped DataChannel.
-     */
-    public DataChannel getChannel() {
-        return channel;
-    }
-
-    /**
-     * Returns null.
-     */
-    public EventBridge getServerEventBridge() {
-        return null;
-    }
-
-    /**
-     * Does nothing.
-     */
-    @Override
-    protected void beforeSendMessage(ClientMessage message) {
-        // noop
-    }
-
-    /**
-     * Dispatches a message to an internal handler.
-     */
-    @Override
-    protected Object doSendMessage(ClientMessage message) throws CayenneRuntimeException {
-
-        ClientMessage processedMessage;
-
-        try {
-            switch (serializationPolicy) {
-                case HESSIAN_SERIALIZATION:
-                    processedMessage = (ClientMessage) HessianUtil
-                            .cloneViaClientServerSerialization(message, channel
-                                    .getEntityResolver());
-                    break;
-
-                case JAVA_SERIALIZATION:
-                    processedMessage = Util.cloneViaSerialization(message);
-                    break;
-
-                default:
-                    processedMessage = message;
-            }
-
-        }
-        catch (Exception ex) {
-            throw new CayenneRuntimeException("Error serializing message", ex);
-        }
-
-        Serializable result = (Serializable) DispatchHelper.dispatch(
-                channel,
-                processedMessage);
-
-        try {
-            switch (serializationPolicy) {
-                case HESSIAN_SERIALIZATION:
-                    return HessianUtil.cloneViaServerClientSerialization(result, channel
-                            .getEntityResolver());
-                case JAVA_SERIALIZATION:
-                    return Util.cloneViaSerialization(result);
-                default:
-                    return result;
-            }
-        }
-        catch (Exception ex) {
-            throw new CayenneRuntimeException("Error deserializing result", ex);
-        }
-
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/HttpClientConnection.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/HttpClientConnection.java
deleted file mode 100644
index f72723722..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/HttpClientConnection.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.rop;
-
-import org.apache.cayenne.CayenneRuntimeException;
-import org.apache.cayenne.di.BeforeScopeEnd;
-import org.apache.cayenne.event.EventBridge;
-import org.apache.cayenne.event.EventBridgeFactory;
-import org.apache.cayenne.remote.BaseConnection;
-import org.apache.cayenne.remote.ClientMessage;
-import org.apache.cayenne.remote.RemoteService;
-import org.apache.cayenne.remote.RemoteSession;
-
-import java.rmi.RemoteException;
-
-public class HttpClientConnection extends BaseConnection {
-
-	private RemoteService remoteService;
-	private RemoteSession session;
-
-	private String sharedSessionName;
-    
-    public HttpClientConnection(RemoteService remoteService, String sharedSession) {
-        this.remoteService = remoteService;
-        this.sharedSessionName = sharedSession;
-    }
-
-    public RemoteSession getSession() {
-        return session;
-    }
-
-	@Override
-	protected void beforeSendMessage(ClientMessage message) throws CayenneRuntimeException {
-		if (session == null) {
-			connect();
-		}
-	}
-
-	@Override
-	protected Object doSendMessage(ClientMessage message) throws CayenneRuntimeException {
-        try {
-            return remoteService.processMessage(message);
-        }
-        catch (CayenneRuntimeException e) {
-            throw e;
-        }
-        catch (Throwable th) {
-            throw new CayenneRuntimeException(th.getMessage(), th);
-        }
-	}
-
-	@Override
-	public EventBridge getServerEventBridge() throws CayenneRuntimeException {
-        if (session == null) {
-            connect();
-        }
-
-        return createServerEventBridge(session);
-	}
-
-    @BeforeScopeEnd
-    public void shutdown() throws RemoteException {
-            remoteService.close();
-    }
-
-	protected synchronized void connect() {
-		if (session != null) {
-			return;
-		}
-        
-        long t0 = System.currentTimeMillis();
-
-		// create server session...
-		try {
-			this.session = (sharedSessionName != null) ? remoteService
-					.establishSharedSession(sharedSessionName) : remoteService
-					.establishSession();
-		}
-		catch (Throwable th) {
-			logger.info(th.getMessage(), th);
-			throw new CayenneRuntimeException(th.getMessage(), th);
-		}
-
-        if (logger.isInfoEnabled()) {
-            long time = System.currentTimeMillis() - t0;
-            logger.info("=== Connected, session: "
-                    + session
-                    + " - took "
-                    + time
-                    + " ms.");
-        }
-	}
-
-    /**
-     * Creates an EventBridge that will listen for server events. Returns null if server
-     * events support is not configured in the descriptor.
-     *
-     * @throws CayenneRuntimeException if EventBridge startup fails for any reason.
-     */
-    protected EventBridge createServerEventBridge(RemoteSession session) throws CayenneRuntimeException {
-
-        if (!session.isServerEventsEnabled()) {
-            return null;
-        }
-
-        try {
-            EventBridgeFactory factory = (EventBridgeFactory) Class.forName(session.getEventBridgeFactory())
-                    .newInstance();
-
-            // must use "name", not the sessionId as an external subject for the
-            // event bridge
-            return factory.createEventBridge(RemoteSession.getSubjects(), session.getName(),
-                    session.getEventBridgeParameters());
-        } catch (Exception ex) {
-            throw new CayenneRuntimeException("Error creating EventBridge.", ex);
-        }
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/HttpClientConnectionProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/HttpClientConnectionProvider.java
deleted file mode 100644
index 3138c434d..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/HttpClientConnectionProvider.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.rop;
-
-import org.apache.cayenne.ConfigurationException;
-import org.apache.cayenne.configuration.RuntimeProperties;
-import org.apache.cayenne.configuration.rop.client.ClientConstants;
-import org.apache.cayenne.di.DIRuntimeException;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.rop.http.HttpROPConnector;
-
-public class HttpClientConnectionProvider implements Provider<ClientConnection> {
-
-    @Inject
-    protected RuntimeProperties runtimeProperties;
-    
-    @Inject
-    protected Provider<ROPSerializationService> serializationServiceProvider;
-
-    @Override
-    public ClientConnection get() throws DIRuntimeException {
-        String sharedSession = runtimeProperties
-                .get(ClientConstants.ROP_SERVICE_SHARED_SESSION_PROPERTY);
-
-        HttpROPConnector ropConnector = createHttpRopConnector();
-        ProxyRemoteService remoteService = new ProxyRemoteService(serializationServiceProvider.get(), ropConnector);
-
-        HttpClientConnection clientConnection = new HttpClientConnection(remoteService, sharedSession);
-        ropConnector.setClientConnection(clientConnection);
-
-        return clientConnection;
-    }
-
-    protected HttpROPConnector createHttpRopConnector() {
-        String url = runtimeProperties.get(ClientConstants.ROP_SERVICE_URL_PROPERTY);
-        if (url == null) {
-            throw new ConfigurationException(
-                    "No property defined for '%s', can't initialize HessianConnection",
-                    ClientConstants.ROP_SERVICE_URL_PROPERTY);
-        }
-
-        String userName = runtimeProperties.get(ClientConstants.ROP_SERVICE_USERNAME_PROPERTY);
-        String password = runtimeProperties.get(ClientConstants.ROP_SERVICE_PASSWORD_PROPERTY);
-
-        long readTimeout = runtimeProperties.getLong(ClientConstants.ROP_SERVICE_TIMEOUT_PROPERTY, -1L);
-
-        HttpROPConnector result = new HttpROPConnector(url, userName, password);
-
-        if (readTimeout > 0) {
-            result.setReadTimeout(readTimeout);
-        }
-
-        return result;
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/ProxyRemoteService.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/ProxyRemoteService.java
deleted file mode 100644
index e2208211f..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/ProxyRemoteService.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.rop;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.remote.ClientMessage;
-import org.apache.cayenne.remote.RemoteService;
-import org.apache.cayenne.remote.RemoteSession;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.rmi.RemoteException;
-
-public class ProxyRemoteService implements RemoteService {
-
-    protected ROPSerializationService serializationService;
-
-    protected ROPConnector ropConnector;
-
-    public ProxyRemoteService(@Inject ROPSerializationService serializationService, @Inject ROPConnector ropConnector) {
-        this.serializationService = serializationService;
-        this.ropConnector = ropConnector;
-    }
-
-    @Override
-    public RemoteSession establishSession() throws RemoteException {
-        try (InputStream is = ropConnector.establishSession()) {
-            return serializationService.deserialize(is, RemoteSession.class);
-        } catch (IOException e) {
-            throw new RemoteException(e.getMessage(), e);
-        }
-    }
-
-    @Override
-    public RemoteSession establishSharedSession(String name) throws RemoteException {
-        try (InputStream is = ropConnector.establishSharedSession(name)) {
-            return serializationService.deserialize(is, RemoteSession.class);
-        } catch (IOException e) {
-            throw new RemoteException(e.getMessage(), e);
-        }
-    }
-
-    @Override
-    public Object processMessage(ClientMessage message) throws RemoteException, Throwable {
-        try (InputStream is = ropConnector.sendMessage(serializationService.serialize(message))) {
-            return serializationService.deserialize(is, Object.class);
-        } catch (IOException e) {
-            throw new RemoteException(e.getMessage(), e);
-        }
-    }
-
-    @Override
-    public void close() throws RemoteException {
-        try {
-            ropConnector.close();
-        } catch (IOException e) {
-            throw new RemoteException("Exception while closing ROP resources", e);
-        }
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/ROPConnector.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/ROPConnector.java
deleted file mode 100644
index 9f350d6f2..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/ROPConnector.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.rop;
-
-import java.io.IOException;
-import java.io.InputStream;
-
-/**
- * ROP network connectivity interface.
- * 
- * @since 4.0
- */
-public interface ROPConnector {
-
-	/**
-	 * Establishes a dedicated session with Cayenne DataChannel, returning session id.
-	 */
-    InputStream establishSession() throws IOException;
-
-	/**
-	 * Creates a new session with the specified or joins an existing one. This method is
-	 * used to bootstrap collaborating clients of a single "group chat".
-	 */
-    InputStream establishSharedSession(String sharedSessionName) throws IOException;
-
-	/**
-	 * Processes message on a remote server, returning the result of such processing.
-	 */
-    InputStream sendMessage(byte[] message) throws IOException;
-
-	/**
-	 * Close all resources related to ROP Connector.
-	 */
-	void close() throws IOException;
-    
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/ROPUtil.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/ROPUtil.java
deleted file mode 100644
index d79d2ba8c..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/ROPUtil.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/*****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- * <p>
- * https://www.apache.org/licenses/LICENSE-2.0
- * <p>
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- ****************************************************************/
-
-package org.apache.cayenne.rop;
-
-import java.util.Map;
-
-public class ROPUtil {
-
-    public static String getLogConnect(String url, String username, boolean password) {
-        return getLogConnect(url, username, password, null);
-    }
-
-    public static String getLogConnect(String url, String username, boolean password, String sharedSessionName) {
-        StringBuilder log = new StringBuilder("Connecting to [");
-        if (username != null) {
-            log.append(username);
-
-            if (password) {
-                log.append(":*******");
-            }
-
-            log.append("@");
-        }
-
-        log.append(url);
-        log.append("]");
-
-        if (sharedSessionName != null) {
-            log.append(" - shared session '").append(sharedSessionName).append("'");
-        } else {
-            log.append(" - dedicated session.");
-        }
-
-        return log.toString();
-    }
-
-    public static String getLogDisconnect(String url, String username, boolean password) {
-        StringBuilder log = new StringBuilder("Disconnecting from [");
-        if (username != null) {
-            log.append(username);
-
-            if (password) {
-                log.append(":*******");
-            }
-
-            log.append("@");
-        }
-
-        log.append(url);
-        log.append("]");
-
-        return log.toString();
-    }
-
-    public static String getParamsAsString(Map<String, String> params) {
-        StringBuilder urlParams = new StringBuilder();
-
-        for (Map.Entry<String, String> entry : params.entrySet()) {
-            if (urlParams.length() > 0) {
-                urlParams.append('&');
-            }
-
-            urlParams.append(entry.getKey());
-            urlParams.append('=');
-            urlParams.append(entry.getValue());
-        }
-
-        return urlParams.toString();
-    }
-
-    public static String getBasicAuth(String username, String password) {
-        if (username != null && password != null) {
-            return "Basic " + base64(username + ":" + password);
-        }
-
-        return null;
-    }
-
-    /**
-     * Creates the Base64 value.
-     */
-    public static String base64(String value) {
-        StringBuffer cb = new StringBuffer();
-
-        int i = 0;
-        for (i = 0; i + 2 < value.length(); i += 3) {
-            long chunk = (int) value.charAt(i);
-            chunk = (chunk << 8) + (int) value.charAt(i + 1);
-            chunk = (chunk << 8) + (int) value.charAt(i + 2);
-
-            cb.append(encode(chunk >> 18));
-            cb.append(encode(chunk >> 12));
-            cb.append(encode(chunk >> 6));
-            cb.append(encode(chunk));
-        }
-
-        if (i + 1 < value.length()) {
-            long chunk = (int) value.charAt(i);
-            chunk = (chunk << 8) + (int) value.charAt(i + 1);
-            chunk <<= 8;
-
-            cb.append(encode(chunk >> 18));
-            cb.append(encode(chunk >> 12));
-            cb.append(encode(chunk >> 6));
-            cb.append('=');
-        } else if (i < value.length()) {
-            long chunk = (int) value.charAt(i);
-            chunk <<= 16;
-
-            cb.append(encode(chunk >> 18));
-            cb.append(encode(chunk >> 12));
-            cb.append('=');
-            cb.append('=');
-        }
-
-        return cb.toString();
-    }
-
-    public static char encode(long d) {
-        d &= 0x3f;
-        if (d < 26) {
-            return (char) (d + 'A');
-        } else if (d < 52) {
-            return (char) (d + 'a' - 26);
-        } else if (d < 62) {
-            return (char) (d + '0' - 52);
-        } else if (d == 62) {
-            return '+';
-        } else {
-            return '/';
-        }
-    }
-
-}
\ No newline at end of file
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/http/ClientHessianSerializationServiceProvider.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/http/ClientHessianSerializationServiceProvider.java
deleted file mode 100644
index 200d69ac5..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/http/ClientHessianSerializationServiceProvider.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.rop.http;
-
-import org.apache.cayenne.di.DIRuntimeException;
-import org.apache.cayenne.di.Provider;
-import org.apache.cayenne.remote.hessian.ClientSerializerFactory;
-import org.apache.cayenne.remote.hessian.HessianConfig;
-import org.apache.cayenne.rop.HessianROPSerializationService;
-import org.apache.cayenne.rop.ROPSerializationService;
-
-public class ClientHessianSerializationServiceProvider implements Provider<ROPSerializationService> {
-
-    public static final String[] CLIENT_SERIALIZER_FACTORIES = new String[] {
-            ClientSerializerFactory.class.getName()
-    };
-
-    @Override
-    public ROPSerializationService get() throws DIRuntimeException {
-        return new HessianROPSerializationService(
-                HessianConfig.createFactory(CLIENT_SERIALIZER_FACTORIES, null));
-    }
-}
diff --git a/cayenne-client/src/main/java/org/apache/cayenne/rop/http/HttpROPConnector.java b/cayenne-client/src/main/java/org/apache/cayenne/rop/http/HttpROPConnector.java
deleted file mode 100644
index 7ed926950..000000000
--- a/cayenne-client/src/main/java/org/apache/cayenne/rop/http/HttpROPConnector.java
+++ /dev/null
@@ -1,166 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.rop.http;
-
-import org.apache.cayenne.remote.RemoteSession;
-import org.apache.cayenne.rop.HttpClientConnection;
-import org.apache.cayenne.rop.ROPConnector;
-import org.apache.cayenne.rop.ROPConstants;
-import org.apache.cayenne.rop.ROPUtil;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.net.URL;
-import java.net.URLConnection;
-import java.nio.charset.StandardCharsets;
-import java.util.HashMap;
-import java.util.Map;
-
-public class HttpROPConnector implements ROPConnector {
-
-    private static final Logger logger = LoggerFactory.getLogger(HttpROPConnector.class);
-
-    public static final String SESSION_COOKIE_NAME = "JSESSIONID";
-
-    private HttpClientConnection clientConnection;
-
-    private String url;
-
-    private String username;
-    private String password;
-
-    private Long readTimeout;
-    
-    public HttpROPConnector(String url, String username, String password) {
-        this.url = url;
-        this.username = username;
-        this.password = password;
-    }
-
-    public void setClientConnection(HttpClientConnection clientConnection) {
-        this.clientConnection = clientConnection;
-    }
-    
-    public void setReadTimeout(Long readTimeout) {
-        this.readTimeout = readTimeout;
-    }
-
-    @Override
-    public InputStream establishSession() throws IOException {
-        if (logger.isInfoEnabled()) {
-            logger.info(ROPUtil.getLogConnect(url, username, password != null));
-        }
-		
-		Map<String, String> requestParams = new HashMap<>();
-		requestParams.put(ROPConstants.OPERATION_PARAMETER, ROPConstants.ESTABLISH_SESSION_OPERATION);
-		
-        return doRequest(requestParams);
-    }
-
-    @Override
-    public InputStream establishSharedSession(String sharedSessionName) throws IOException {
-        if (logger.isInfoEnabled()) {
-            logger.info(ROPUtil.getLogConnect(url, username, password != null, sharedSessionName));
-        }
-
-		Map<String, String> requestParams = new HashMap<>();
-		requestParams.put(ROPConstants.OPERATION_PARAMETER, ROPConstants.ESTABLISH_SHARED_SESSION_OPERATION);
-		requestParams.put(ROPConstants.SESSION_NAME_PARAMETER, sharedSessionName);
-
-		return doRequest(requestParams);
-    }
-
-    @Override
-    public InputStream sendMessage(byte[] message) throws IOException {
-        return doRequest(message);
-    }
-
-    @Override
-    public void close() throws IOException {
-        if (logger.isInfoEnabled()) {
-            logger.info(ROPUtil.getLogDisconnect(url, username, password != null));
-        }
-    }
-
-    protected InputStream doRequest(Map<String, String> params) throws IOException {
-        URLConnection connection = new URL(url).openConnection();
-
-        if (readTimeout != null) {
-            connection.setReadTimeout(readTimeout.intValue());
-        }
-
-        addAuthHeader(connection);
-
-        connection.setDoOutput(true);
-
-        connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
-        connection.setRequestProperty("charset", "utf-8");
-
-        try (OutputStream output = connection.getOutputStream()) {
-            output.write(ROPUtil.getParamsAsString(params).getBytes(StandardCharsets.UTF_8));
-            output.flush();
-        }
-
-        return connection.getInputStream();
-    }
-
-    protected InputStream doRequest(byte[] data) throws IOException {
-        URLConnection connection = new URL(url).openConnection();
-
-        if (readTimeout != null) {
-            connection.setReadTimeout(readTimeout.intValue());
-        }
-
-        addAuthHeader(connection);
-        addSessionCookie(connection);
-        connection.setDoOutput(true);
-
-        connection.setRequestProperty("Content-Type", "application/octet-stream");
-
-        if (data != null) {
-            try (OutputStream output = connection.getOutputStream()) {
-                output.write(data);
-                output.flush();
-            }
-        }
-
-        return connection.getInputStream();
-    }
-
-    protected void addAuthHeader(URLConnection connection) {
-        String basicAuth = ROPUtil.getBasicAuth(username, password);
-
-        if (basicAuth != null) {
-            connection.addRequestProperty("Authorization", basicAuth);
-        }
-    }
-
-    protected void addSessionCookie(URLConnection connection) {
-        RemoteSession session = clientConnection.getSession();
-        if (session != null && session.getSessionId() != null) {
-            connection.addRequestProperty("Cookie", SESSION_COOKIE_NAME
-                    + "="
-                    + session.getSessionId());
-        }
-    }
-
-}
diff --git a/cayenne-client/src/main/resources/META-INF/services/org.apache.cayenne.configuration.rop.client.CayenneClientModuleProvider b/cayenne-client/src/main/resources/META-INF/services/org.apache.cayenne.configuration.rop.client.CayenneClientModuleProvider
deleted file mode 100644
index dda3d4d3d..000000000
--- a/cayenne-client/src/main/resources/META-INF/services/org.apache.cayenne.configuration.rop.client.CayenneClientModuleProvider
+++ /dev/null
@@ -1,20 +0,0 @@
-##################################################################
-#   Licensed to the Apache Software Foundation (ASF) under one
-#  or more contributor license agreements.  See the NOTICE file
-#  distributed with this work for additional information
-#  regarding copyright ownership.  The ASF licenses this file
-#  to you under the Apache License, Version 2.0 (the
-#  "License"); you may not use this file except in compliance
-#  with the License.  You may obtain a copy of the License at
-#
-#    https://www.apache.org/licenses/LICENSE-2.0
-#
-#  Unless required by applicable law or agreed to in writing,
-#  software distributed under the License is distributed on an
-#  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-#  KIND, either express or implied.  See the License for the
-#  specific language governing permissions and limitations
-#  under the License.
-##################################################################
-
-org.apache.cayenne.configuration.rop.client.MainCayenneClientModuleProvider
\ No newline at end of file
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextCayenneIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextCayenneIT.java
deleted file mode 100644
index 8940ab936..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextCayenneIT.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.SQLTemplate;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextCayenneIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Test
-    public void testObjectForPK() throws Exception {
-
-        context.performGenericQuery(new SQLTemplate(
-                ClientMtTable1.class,
-                "insert into MT_TABLE1 "
-                        + "(TABLE1_ID, GLOBAL_ATTRIBUTE1, SERVER_ATTRIBUTE1) "
-                        + "values (1, 'g1', 's1')"));
-
-        ClientMtTable1 o = Cayenne.objectForPK(context, ClientMtTable1.class, 1);
-        assertNotNull(o);
-        assertEquals("g1", o.getGlobalAttribute1());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextClientChannelEventsIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextClientChannelEventsIT.java
deleted file mode 100644
index ae63b45bd..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextClientChannelEventsIT.java
+++ /dev/null
@@ -1,353 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.configuration.rop.client.ClientConstants;
-import org.apache.cayenne.configuration.rop.client.ClientRuntime;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectIdQuery;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.ClientMtTable4;
-import org.apache.cayenne.testdo.mt.ClientMtTable5;
-import org.apache.cayenne.unit.di.client.ClientCaseContextsSync;
-import org.apache.cayenne.unit.di.client.ClientRuntimeProperty;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.*;
-
-/**
- * Tests peer context synchronization via ClientChannel events.
- */
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-@ClientRuntimeProperty({
-        ClientConstants.ROP_CHANNEL_EVENTS_PROPERTY, "true"
-})
-public class CayenneContextClientChannelEventsIT extends ClientCaseContextsSync {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private ClientRuntime runtime;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-    private TableHelper tMtTable4;
-    private TableHelper tMtTable5;
-    private TableHelper tMtJoin45;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-
-        tMtTable4 = new TableHelper(dbHelper, "MT_TABLE4");
-        tMtTable4.setColumns("ID");
-
-        tMtTable5 = new TableHelper(dbHelper, "MT_TABLE5");
-        tMtTable5.setColumns("ID");
-
-        tMtJoin45 = new TableHelper(dbHelper, "MT_JOIN45");
-        tMtJoin45.setColumns("TABLE4_ID", "TABLE5_ID");
-    }
-
-    @Test
-    public void testSyncNewObject() throws Exception {
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-        assertNotSame(c1, c2);
-
-        ClientMtTable1 o1 = c1.newObject(ClientMtTable1.class);
-        o1.setGlobalAttribute1("X");
-        c1.commitChanges();
-
-        ClientMtTable1 o2 = (ClientMtTable1) c2.getGraphManager().getNode(
-                o1.getObjectId());
-
-        assertNull(o2);
-        // now fetch it fresh
-
-        o2 = (ClientMtTable1) c2.performQuery(new ObjectIdQuery(o1.getObjectId())).get(0);
-        assertNotNull(o2);
-
-        assertEquals("X", o2.getGlobalAttribute1());
-        assertEquals(PersistenceState.COMMITTED, o2.getPersistenceState());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncNewDeletedObject() throws Exception {
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-        assertNotSame(c1, c2);
-
-        // insert, then delete - this shouldn't propagate via an event.
-        ClientMtTable1 o1 = c1.newObject(ClientMtTable1.class);
-        o1.setGlobalAttribute1("X");
-        c1.deleteObjects(o1);
-
-        // introduce some other change so that commit can go ahead...
-        ClientMtTable1 o1x = c1.newObject(ClientMtTable1.class);
-        o1x.setGlobalAttribute1("Y");
-        c1.commitChanges();
-
-        ClientMtTable1 o2 = (ClientMtTable1) c2.getGraphManager().getNode(
-                o1.getObjectId());
-
-        assertNull(o2);
-
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncNewObjectIntoDirtyContext() throws Exception {
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-        assertNotSame(c1, c2);
-
-        // make sure c2 has uncommitted changes
-        c2.newObject(ClientMtTable1.class);
-
-        ClientMtTable1 o1 = c1.newObject(ClientMtTable1.class);
-        o1.setGlobalAttribute1("X");
-        c1.commitChanges();
-
-        ClientMtTable1 o2 = (ClientMtTable1) c2.getGraphManager().getNode(
-                o1.getObjectId());
-        assertNull(o2);
-
-        // now fetch it fresh
-
-        o2 = (ClientMtTable1) c2.performQuery(new ObjectIdQuery(o1.getObjectId())).get(0);
-        assertNotNull(o2);
-        assertEquals("X", o2.getGlobalAttribute1());
-        assertEquals(PersistenceState.COMMITTED, o2.getPersistenceState());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertTrue(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncSimpleProperty() throws Exception {
-
-        tMtTable1.insert(1, "g1", "s1");
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-        assertNotSame(c1, c2);
-
-        ClientMtTable1 o1 = (ClientMtTable1) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 1)));
-
-        ClientMtTable1 o2 = (ClientMtTable1) Cayenne.objectForQuery(
-                c2,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 1)));
-
-        assertEquals("g1", o1.getGlobalAttribute1());
-        assertEquals("g1", o2.getGlobalAttribute1());
-
-        o1.setGlobalAttribute1("X");
-        c1.commitChanges();
-        
-        // let the events propagate to peers
-        Thread.sleep(500);
-
-        assertEquals("X", o2.getGlobalAttribute1());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncToOneRelationship() throws Exception {
-
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable1.insert(2, "g2", "s2");
-        tMtTable2.insert(1, 1, "g1");
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-
-        ClientMtTable2 o1 = (ClientMtTable2) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable2", "TABLE2_ID", 1)));
-
-        ClientMtTable2 o2 = (ClientMtTable2) Cayenne.objectForQuery(
-                c2,
-                new ObjectIdQuery(ObjectId.of("MtTable2", "TABLE2_ID", 1)));
-
-        assertEquals("g1", o1.getTable1().getGlobalAttribute1());
-        assertEquals("g1", o2.getTable1().getGlobalAttribute1());
-
-        ClientMtTable1 o1r = (ClientMtTable1) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 2)));
-        o1.setTable1(o1r);
-        c1.commitChanges();
-        
-        // let the events propagate to peers
-        Thread.sleep(500);
-
-        assertEquals("g2", o2.getTable1().getGlobalAttribute1());
-        assertEquals(o1r.getObjectId(), o2.getTable1().getObjectId());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncToManyRelationship() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable2.insert(1, 1, "g1");
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-
-        ClientMtTable1 o1 = (ClientMtTable1) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 1)));
-
-        ClientMtTable1 o2 = (ClientMtTable1) Cayenne.objectForQuery(
-                c2,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 1)));
-
-        assertEquals(1, o1.getTable2Array().size());
-        assertEquals(1, o2.getTable2Array().size());
-
-        ClientMtTable2 o1r = c1.newObject(ClientMtTable2.class);
-        o1r.setGlobalAttribute("X");
-        o1.addToTable2Array(o1r);
-
-        c1.commitChanges();
-        
-        // let the events propagate to peers
-        Thread.sleep(500);
-
-        assertEquals(2, o1.getTable2Array().size());
-        assertEquals(2, o2.getTable2Array().size());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncToManyRelationship1() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable2.insert(1, 1, "g1");
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-
-        ClientMtTable1 o1 = (ClientMtTable1) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 1)));
-
-        // do not resolve objects in question in the second context and see if the merge
-        // causes any issues...
-
-        assertEquals(1, o1.getTable2Array().size());
-
-        ClientMtTable2 o1r = c1.newObject(ClientMtTable2.class);
-        o1r.setGlobalAttribute("X");
-        o1.addToTable2Array(o1r);
-
-        c1.commitChanges();
-
-        assertEquals(2, o1.getTable2Array().size());
-
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-
-        ClientMtTable1 o2 = (ClientMtTable1) Cayenne.objectForQuery(
-                c2,
-                new ObjectIdQuery(ObjectId.of("MtTable1", "TABLE1_ID", 1)));
-        assertEquals(2, o2.getTable2Array().size());
-    }
-
-    @Test
-    public void testSyncManyToManyRelationship() throws Exception {
-        tMtTable4.insert(1);
-        tMtTable5.insert(1);
-        tMtTable5.insert(2);
-        tMtJoin45.insert(1, 1);
-        tMtJoin45.insert(1, 2);
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-
-        ClientMtTable4 o1 = (ClientMtTable4) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable4", "ID", 1)));
-
-        ClientMtTable4 o2 = (ClientMtTable4) Cayenne.objectForQuery(
-                c2,
-                new ObjectIdQuery(ObjectId.of("MtTable4", "ID", 1)));
-
-        assertEquals(2, o1.getTable5s().size());
-        assertEquals(2, o2.getTable5s().size());
-
-        ClientMtTable5 o1r = (ClientMtTable5) Cayenne.objectForQuery(
-                c1,
-                new ObjectIdQuery(ObjectId.of("MtTable5", "ID", 1)));
-        o1.removeFromTable5s(o1r);
-
-        c1.commitChanges();
-        // let the events propagate to peers
-        Thread.sleep(500);
-
-        assertEquals(1, o1.getTable5s().size());
-        assertEquals(1, o2.getTable5s().size());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-
-    @Test
-    public void testSyncManyToManyRelationship1() throws Exception {
-
-        CayenneContext c1 = (CayenneContext) runtime.newContext();
-        CayenneContext c2 = (CayenneContext) runtime.newContext();
-
-        ClientMtTable4 o1 = c1.newObject(ClientMtTable4.class);
-        ClientMtTable5 o1r = c1.newObject(ClientMtTable5.class);
-        c1.commitChanges();
-
-        ClientMtTable4 o2 = c2.localObject(o1);
-        ClientMtTable5 o2r = c2.localObject(o1r);
-
-        o2.addToTable5s(o2r);
-        c2.commitChanges();
-
-        assertEquals(1, o1.getTable5s().size());
-        assertEquals(1, o2.getTable5s().size());
-        assertFalse(c1.internalGraphManager().hasChanges());
-        assertFalse(c2.internalGraphManager().hasChanges());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextDeleteRulesIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextDeleteRulesIT.java
deleted file mode 100644
index 61f132879..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextDeleteRulesIT.java
+++ /dev/null
@@ -1,123 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.testdo.deleterules.ClientDeleteCascade;
-import org.apache.cayenne.testdo.deleterules.ClientDeleteDeny;
-import org.apache.cayenne.testdo.deleterules.ClientDeleteNullify;
-import org.apache.cayenne.testdo.deleterules.ClientDeleteRule;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertTrue;
-import static org.junit.Assert.fail;
-
-@UseServerRuntime(CayenneProjects.DELETE_RULES_PROJECT)
-public class CayenneContextDeleteRulesIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Test
-    public void testNullifyToOne() {
-
-        ClientDeleteNullify object = context.newObject(ClientDeleteNullify.class);
-        object.setName("object");
-
-        ClientDeleteRule related = context.newObject(ClientDeleteRule.class);
-        object.setName("related");
-
-        object.setNullify(related);
-        context.commitChanges();
-
-        context.deleteObjects(object);
-        assertFalse(related.getFromNullify().contains(object));
-        assertNull(object.getNullify());
-
-        // And be sure that the commit works afterwards, just for sanity
-        context.commitChanges();
-    }
-
-    @Test
-    public void testDenyToOne() {
-
-        ClientDeleteDeny object = context.newObject(ClientDeleteDeny.class);
-        ClientDeleteRule related = context.newObject(ClientDeleteRule.class);
-        object.setDeny(related);
-        context.commitChanges();
-
-        try {
-            context.deleteObjects(object);
-            fail("Should have thrown an exception");
-        }
-        catch (DeleteDenyException e) {
-            // expected
-        }
-
-        object.setDeny(null);
-        context.deleteObjects(object);
-        context.commitChanges();
-    }
-
-    @Test
-    public void testCascadeToOne() {
-
-        ClientDeleteCascade object = context.newObject(ClientDeleteCascade.class);
-        object.setName("object");
-
-        ClientDeleteRule related = context.newObject(ClientDeleteRule.class);
-        object.setName("related");
-
-        object.setCascade(related);
-        context.commitChanges();
-
-        context.deleteObjects(object);
-        assertEquals(PersistenceState.DELETED, related.getPersistenceState());
-        assertTrue(context.deletedObjects().contains(related));
-
-        // And be sure that the commit works afterwards, just for sanity
-        context.commitChanges();
-    }
-
-    @Test
-    public void testCascadeToOneNewObject() {
-
-        ClientDeleteRule related = context.newObject(ClientDeleteRule.class);
-        context.commitChanges();
-
-        ClientDeleteCascade object = context.newObject(ClientDeleteCascade.class);
-        object.setName("object");
-        object.setCascade(related);
-
-        context.deleteObjects(object);
-        assertEquals(PersistenceState.TRANSIENT, object.getPersistenceState());
-        assertEquals(PersistenceState.DELETED, related.getPersistenceState());
-        assertFalse(context.deletedObjects().contains(object));
-        assertTrue(context.deletedObjects().contains(related));
-
-        context.commitChanges();
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextEJBQLIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextEJBQLIT.java
deleted file mode 100644
index 55c2217f7..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextEJBQLIT.java
+++ /dev/null
@@ -1,93 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.EJBQLQuery;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextEJBQLIT extends ClientCase {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private CayenneContext context;
-
-    private TableHelper tMtTable1;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-    }
-
-    private void createTwoRecords() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable1.insert(2, "g2", "s2");
-    }
-
-    @Test
-    public void testEJBQLSelect() throws Exception {
-        createTwoRecords();
-
-        EJBQLQuery query = new EJBQLQuery("SELECT a FROM MtTable1 a");
-        List<ClientMtTable1> results = context.performQuery(query);
-
-        assertEquals(2, results.size());
-    }
-
-    @Test
-    public void testEJBQLSelectScalar() throws Exception {
-        createTwoRecords();
-
-        EJBQLQuery query = new EJBQLQuery("SELECT COUNT(a) FROM MtTable1 a");
-
-        List<Long> results = context.performQuery(query);
-        assertEquals(Long.valueOf(2), results.get(0));
-    }
-
-    @Test
-    public void testEJBQLSelectMixed() throws Exception {
-        createTwoRecords();
-
-        EJBQLQuery query = new EJBQLQuery(
-                "SELECT COUNT(a), a, a.serverAttribute1 FROM MtTable1 a Group By a ORDER BY a.serverAttribute1");
-
-        List<Object[]> results = context.performQuery(query);
-
-        assertEquals(2, results.size());
-        assertEquals(Long.valueOf(1), results.get(0)[0]);
-        assertTrue(results.get(0)[1] instanceof ClientMtTable1);
-        assertEquals("s1", results.get(0)[2]);
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextGraphDiffCompressorIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextGraphDiffCompressorIT.java
deleted file mode 100644
index 6cf88524f..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextGraphDiffCompressorIT.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.unit.di.DataChannelInterceptor;
-import org.apache.cayenne.unit.di.DataChannelSyncStats;
-import org.apache.cayenne.unit.di.UnitTestClosure;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextGraphDiffCompressorIT extends ClientCase {
-
-    @Inject(ClientCase.ROP_CLIENT_KEY)
-    protected DataChannelInterceptor clientServerInterceptor;
-
-    @Inject
-    protected CayenneContext context;
-
-    @Test
-    public void testMultipleSimpleProperties() {
-
-        ClientMtTable1 o1 = context.newObject(ClientMtTable1.class);
-        o1.setGlobalAttribute1("v1");
-        o1.setGlobalAttribute1("v2");
-
-        DataChannelSyncStats stats = clientServerInterceptor
-                .runWithSyncStatsCollection(new UnitTestClosure() {
-
-                    public void execute() {
-                        context.commitChanges();
-                    }
-                });
-
-        assertEquals(1, stats.nodePropertiesChanged);
-        assertEquals(1, stats.nodesCreated);
-    }
-
-    @Test
-    public void testComplimentaryArcs() {
-
-        ClientMtTable1 o1 = context.newObject(ClientMtTable1.class);
-        ClientMtTable2 o2 = context.newObject(ClientMtTable2.class);
-        o2.setTable1(o1);
-        o2.setTable1(null);
-
-        DataChannelSyncStats stats = clientServerInterceptor
-                .runWithSyncStatsCollection(new UnitTestClosure() {
-
-                    public void execute() {
-                        context.commitChanges();
-                    }
-                });
-
-        assertEquals(0, stats.nodePropertiesChanged);
-        assertEquals(2, stats.nodesCreated);
-        assertEquals(0, stats.arcsCreated);
-        assertEquals(0, stats.arcsDeleted);
-    }
-
-    @Test
-    public void testDelete() {
-
-        ClientMtTable1 o1 = context.newObject(ClientMtTable1.class);
-        o1.setGlobalAttribute1("v1");
-        context.deleteObjects(o1);
-
-        DataChannelSyncStats stats = clientServerInterceptor
-                .runWithSyncStatsCollection(new UnitTestClosure() {
-
-                    public void execute() {
-                        context.commitChanges();
-                    }
-                });
-        assertEquals(0, stats.nodePropertiesChanged);
-        assertEquals(0, stats.nodesCreated);
-        assertEquals(0, stats.nodesRemoved);
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextIT.java
deleted file mode 100644
index 7a864f7f3..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextIT.java
+++ /dev/null
@@ -1,342 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.event.DefaultEventManager;
-import org.apache.cayenne.event.EventManager;
-import org.apache.cayenne.event.MockEventManager;
-import org.apache.cayenne.graph.CompoundDiff;
-import org.apache.cayenne.graph.GraphDiff;
-import org.apache.cayenne.graph.NodeIdChangeOperation;
-import org.apache.cayenne.map.DataMap;
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.map.ObjEntity;
-import org.apache.cayenne.query.Query;
-import org.apache.cayenne.remote.BootstrapMessage;
-import org.apache.cayenne.remote.ClientChannel;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.ClientMessage;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.apache.cayenne.util.GenericResponse;
-import org.junit.After;
-import org.junit.Test;
-import org.mockito.invocation.InvocationOnMock;
-import org.mockito.stubbing.Answer;
-
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNotSame;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextIT extends ClientCase {
-
-	@Inject
-	private ObjectContext serverContext;
-
-	private DefaultEventManager eventManager;
-
-	@After
-	public void cleanUp() {
-		if(eventManager != null) {
-			eventManager.shutdown();
-			eventManager = null;
-		}
-	}
-
-	@Test
-	public void testConstructor() {
-
-		CayenneContext context = new CayenneContext();
-
-		// test default property parameters
-		assertNotNull(context.getGraphManager());
-		assertNull(context.channel);
-
-		MockDataChannel channel = new MockDataChannel();
-		context.setChannel(channel);
-		assertSame(channel, context.getChannel());
-	}
-
-	@Test
-	public void testChannel() {
-		MockDataChannel channel = new MockDataChannel();
-		CayenneContext context = new CayenneContext(channel);
-
-		assertSame(channel, context.getChannel());
-	}
-
-	@Test
-	public void testCommitUnchanged() {
-
-		MockDataChannel channel = new MockDataChannel();
-		CayenneContext context = new CayenneContext(channel);
-
-		// no context changes so no connector access is expected
-		context.commitChanges();
-		assertTrue(channel.getRequestObjects().isEmpty());
-	}
-
-	@Test
-	public void testCommitCommandExecuted() {
-
-		MockDataChannel channel = new MockDataChannel(mock(GraphDiff.class));
-		channel.setEntityResolver(serverContext.getEntityResolver().getClientEntityResolver());
-		CayenneContext context = new CayenneContext(channel);
-
-		// test that a command is being sent via connector on commit...
-
-		context.internalGraphManager().nodePropertyChanged(ObjectId.of("MtTable1"), "x", "y", "z");
-
-		context.commitChanges();
-		assertEquals(1, channel.getRequestObjects().size());
-
-		// expect a sync/commit chain
-		Object mainMessage = channel.getRequestObjects().iterator().next();
-		assertTrue(mainMessage instanceof GraphDiff);
-	}
-
-	@Test
-	public void testCommitChangesNew() {
-		final CompoundDiff diff = new CompoundDiff();
-		final Object newObjectId = ObjectId.of("test", "key", "generated");
-		eventManager = new DefaultEventManager(0);
-
-		// test that ids that are passed back are actually propagated to the
-		// right
-		// objects...
-
-		MockDataChannel channel = new MockDataChannel() {
-
-			@Override
-			public GraphDiff onSync(ObjectContext originatingContext, GraphDiff changes, int syncType) {
-
-				return diff;
-			}
-
-			// must provide a channel with working event manager
-			@Override
-			public EventManager getEventManager() {
-				return eventManager;
-			}
-		};
-
-		CayenneContext context = new CayenneContext(channel);
-		ObjEntity entity = new ObjEntity("test_entity");
-		entity.setClassName(MockPersistentObject.class.getName());
-
-		DataMap dataMap = new DataMap("test");
-		dataMap.addObjEntity(entity);
-		Collection<DataMap> entities = Collections.singleton(dataMap);
-		context.setEntityResolver(new EntityResolver(entities));
-		Persistent object = context.newObject(MockPersistentObject.class);
-
-		// record change here to make it available to the anonymous connector
-		// method..
-		diff.add(new NodeIdChangeOperation(object.getObjectId(), newObjectId));
-
-		// check that a generated object ID is assigned back to the object...
-		assertNotSame(newObjectId, object.getObjectId());
-		context.commitChanges();
-		assertSame(newObjectId, object.getObjectId());
-		assertSame(object, context.graphManager.getNode(newObjectId));
-	}
-
-	@Test
-	public void testNewObject() {
-
-		CayenneContext context = new CayenneContext(new MockDataChannel());
-
-		ObjEntity entity = new ObjEntity("test_entity");
-		entity.setClassName(MockPersistentObject.class.getName());
-
-		DataMap dataMap = new DataMap("test");
-		dataMap.addObjEntity(entity);
-		Collection<DataMap> entities = Collections.singleton(dataMap);
-		context.setEntityResolver(new EntityResolver(entities));
-
-		Persistent object = context.newObject(MockPersistentObject.class);
-		assertNotNull(object);
-		assertTrue(object instanceof MockPersistentObject);
-		assertEquals(PersistenceState.NEW, object.getPersistenceState());
-		assertSame(context, object.getObjectContext());
-		assertTrue(context.internalGraphManager().dirtyNodes(PersistenceState.NEW).contains(object));
-		assertNotNull(object.getObjectId());
-		assertTrue(object.getObjectId().isTemporary());
-	}
-
-	@Test
-	public void testDeleteObject() {
-
-		CayenneContext context = new CayenneContext(new MockDataChannel());
-		ObjEntity entity = new ObjEntity("test_entity");
-		entity.setClassName(MockPersistentObject.class.getName());
-
-		DataMap dataMap = new DataMap("test");
-		dataMap.addObjEntity(entity);
-		Collection<DataMap> entities = Collections.singleton(dataMap);
-		context.setEntityResolver(new EntityResolver(entities));
-
-		// TRANSIENT ... should quietly ignore it
-		Persistent transientObject = new MockPersistentObject();
-		context.deleteObjects(transientObject);
-		assertEquals(PersistenceState.TRANSIENT, transientObject.getPersistenceState());
-
-		// NEW ... should make it TRANSIENT
-		// create via context to make sure that object store would register it
-		Persistent newObject = context.newObject(MockPersistentObject.class);
-		assertNotNull(newObject.getObjectContext());
-		context.deleteObjects(newObject);
-		assertNull(newObject.getObjectContext());
-		assertEquals(PersistenceState.TRANSIENT, newObject.getPersistenceState());
-		assertFalse(context.internalGraphManager().dirtyNodes().contains(newObject.getObjectId()));
-
-		// see CAY-547 for details...
-		assertFalse(context.internalGraphManager().dirtyNodes().contains(null));
-
-		// COMMITTED
-		Persistent committed = new MockPersistentObject();
-		committed.setPersistenceState(PersistenceState.COMMITTED);
-		committed.setObjectId(ObjectId.of("test_entity", "key", "value1"));
-		committed.setObjectContext(context);
-		context.deleteObjects(committed);
-		assertEquals(PersistenceState.DELETED, committed.getPersistenceState());
-
-		// MODIFIED
-		Persistent modified = new MockPersistentObject();
-		modified.setPersistenceState(PersistenceState.MODIFIED);
-		modified.setObjectId(ObjectId.of("test_entity", "key", "value2"));
-		modified.setObjectContext(context);
-		context.deleteObjects(modified);
-		assertEquals(PersistenceState.DELETED, modified.getPersistenceState());
-
-		// DELETED
-		Persistent deleted = new MockPersistentObject();
-		deleted.setPersistenceState(PersistenceState.DELETED);
-		deleted.setObjectId(ObjectId.of("test_entity", "key", "value3"));
-		deleted.setObjectContext(context);
-		context.deleteObjects(deleted);
-		assertEquals(PersistenceState.DELETED, committed.getPersistenceState());
-	}
-
-	@Test
-	public void testBeforePropertyReadShouldInflateHollow() {
-
-        ObjectId gid = ObjectId.of("MtTable1", "a", "b");
-		final ClientMtTable1 inflated = new ClientMtTable1();
-		inflated.setPersistenceState(PersistenceState.COMMITTED);
-		inflated.setObjectId(gid);
-		inflated.setGlobalAttribute1("abc");
-
-		ClientConnection connection = mock(ClientConnection.class);
-		when(connection.sendMessage((ClientMessage) any())).thenAnswer(new Answer<Object>() {
-
-			public Object answer(InvocationOnMock invocation) {
-				ClientMessage arg = (ClientMessage) invocation.getArguments()[0];
-
-				if (arg instanceof BootstrapMessage) {
-					return new EntityResolver();
-				} else {
-					return new GenericResponse(Arrays.asList(inflated));
-				}
-			}
-		});
-
-		ClientChannel channel = new ClientChannel(connection, false, new MockEventManager(), false);
-
-		// check that a HOLLOW object is infalted on "beforePropertyRead"
-		ClientMtTable1 hollow = new ClientMtTable1();
-		hollow.setPersistenceState(PersistenceState.HOLLOW);
-		hollow.setObjectId(gid);
-
-		final boolean[] selectExecuted = new boolean[1];
-		CayenneContext context = new CayenneContext(channel) {
-
-			@Override
-			public List<?> performQuery(Query query) {
-				selectExecuted[0] = true;
-				return super.performQuery(query);
-			}
-		};
-
-		context.setEntityResolver(serverContext.getEntityResolver().getClientEntityResolver());
-
-		context.graphManager.registerNode(hollow.getObjectId(), hollow);
-
-		// testing this...
-		context.prepareForAccess(hollow, ClientMtTable1.GLOBAL_ATTRIBUTE1.getName(), false);
-		assertTrue(selectExecuted[0]);
-		assertSame(hollow, context.getGraphManager().getNode(gid));
-		assertEquals(inflated.getGlobalAttribute1Direct(), hollow.getGlobalAttribute1Direct());
-		assertEquals(PersistenceState.COMMITTED, hollow.getPersistenceState());
-	}
-
-	@Test
-	public void testBeforeHollowDeleteShouldChangeStateToCommited() {
-
-        ObjectId gid = ObjectId.of("MtTable1", "a", "b");
-		final ClientMtTable1 inflated = new ClientMtTable1();
-		inflated.setPersistenceState(PersistenceState.COMMITTED);
-		inflated.setObjectId(gid);
-		inflated.setGlobalAttribute1("abc");
-
-		ClientConnection connection = mock(ClientConnection.class);
-		when(connection.sendMessage((ClientMessage) any())).thenAnswer(new Answer<Object>() {
-
-			public Object answer(InvocationOnMock invocation) {
-				ClientMessage arg = (ClientMessage) invocation.getArguments()[0];
-
-				if (arg instanceof BootstrapMessage) {
-					return new EntityResolver();
-				} else {
-					return new GenericResponse(Arrays.asList(inflated));
-				}
-			}
-		});
-		ClientChannel channel = new ClientChannel(connection, false, new MockEventManager(), false);
-
-		CayenneContext context = new CayenneContext(channel);
-		context.setEntityResolver(serverContext.getEntityResolver().getClientEntityResolver());
-		ClientMtTable1 hollow = context.localObject(inflated);
-		assertEquals(PersistenceState.HOLLOW, hollow.getPersistenceState());
-
-		// testing this...
-		context.deleteObjects(hollow);
-		assertSame(hollow, context.getGraphManager().getNode(gid));
-		assertEquals(inflated.getGlobalAttribute1Direct(), hollow.getGlobalAttribute1Direct());
-		assertEquals(PersistenceState.DELETED, hollow.getPersistenceState());
-	}
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextInheritanceIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextInheritanceIT.java
deleted file mode 100644
index f164a0aba..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextInheritanceIT.java
+++ /dev/null
@@ -1,146 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable1Subclass1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.sql.Types;
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextInheritanceIT extends ClientCase {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private CayenneContext context;
-
-    private TableHelper tMtTable1;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns(
-                "TABLE1_ID",
-                "GLOBAL_ATTRIBUTE1",
-                "SERVER_ATTRIBUTE1",
-                "SUBCLASS_ATTRIBUTE1").setColumnTypes(
-                Types.INTEGER,
-                Types.VARCHAR,
-                Types.VARCHAR,
-                Types.VARCHAR);
-    }
-
-    @Test
-    public void testInsertSubclass() throws Exception {
-
-        ClientMtTable1Subclass1 object = context.newObject(ClientMtTable1Subclass1.class);
-        object.setGlobalAttribute1("sub1");
-        object.setServerAttribute1("sa1");
-        object.setSubclass1Attribute1("suba1");
-
-        context.commitChanges();
-
-        assertEquals(1, tMtTable1.getRowCount());
-        assertEquals("sub1", tMtTable1.getString("GLOBAL_ATTRIBUTE1"));
-        assertEquals("sa1", tMtTable1.getString("SERVER_ATTRIBUTE1"));
-        assertEquals("suba1", tMtTable1.getString("SUBCLASS_ATTRIBUTE1"));
-    }
-
-    @Test
-    public void testPerformQueryInheritanceLeaf() throws Exception {
-
-        tMtTable1.insert(1, "xxx", "yyy", null);
-        tMtTable1.insert(2, "sub1", "zzz", "sa1");
-        tMtTable1.insert(3, "1111", "aaa", null);
-
-        List<ClientMtTable1Subclass1> objects = ObjectSelect.query(ClientMtTable1Subclass1.class).select(context);
-
-        assertEquals(1, objects.size());
-        assertEquals("sa1", objects.get(0).getSubclass1Attribute1());
-    }
-
-    @Test
-    public void testPerformQueryInheritanceSuper() throws Exception {
-
-        tMtTable1.insert(1, "a", "yyy", null);
-        tMtTable1.insert(2, "sub1", "zzz", "sa1");
-        tMtTable1.insert(3, "z", "aaa", null);
-
-        List<ClientMtTable1> objects = ObjectSelect.query(ClientMtTable1.class).select(context);
-
-        assertEquals(3, objects.size());
-
-        int checkedFields = 0;
-        for (ClientMtTable1 object : objects) {
-            Integer id = (Integer) object.getObjectId().getIdSnapshot().get("TABLE1_ID");
-            if (id == 1) {
-                assertEquals("a", object.getGlobalAttribute1());
-                checkedFields++;
-            } else if (id == 2) {
-                assertEquals("sa1", ((ClientMtTable1Subclass1) object).getSubclass1Attribute1());
-                checkedFields++;
-            }
-
-        }
-        assertEquals(2, checkedFields);
-    }
-
-    @Test
-    public void testPerformQueryWithQualifierInheritanceSuper() throws Exception {
-
-        tMtTable1.insert(1, "a", "XX", null);
-        tMtTable1.insert(2, "sub1", "XXA", "sa1");
-        tMtTable1.insert(3, "z", "MM", null);
-
-        List<ClientMtTable1> objects = ObjectSelect.query(ClientMtTable1.class)
-                .where(ClientMtTable1.SERVER_ATTRIBUTE1.like("X%"))
-                .select(context);
-
-        assertEquals(2, objects.size());
-
-        int checkedFields = 0;
-        for (ClientMtTable1 object : objects) {
-            Integer id = (Integer) object.getObjectId().getIdSnapshot().get("TABLE1_ID");
-            if (id == 1) {
-                assertEquals("a", object.getGlobalAttribute1());
-                checkedFields++;
-            } else if (id == 2) {
-                assertEquals("sa1", ((ClientMtTable1Subclass1) object).getSubclass1Attribute1());
-                checkedFields++;
-            }
-
-        }
-        assertEquals(2, checkedFields);
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMapRelationshipIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMapRelationshipIT.java
deleted file mode 100644
index bd1ffe810..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMapRelationshipIT.java
+++ /dev/null
@@ -1,119 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectIdQuery;
-import org.apache.cayenne.query.RefreshQuery;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.map_to_many.ClientIdMapToMany;
-import org.apache.cayenne.testdo.map_to_many.ClientIdMapToManyTarget;
-import org.apache.cayenne.testdo.map_to_many.IdMapToMany;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-
-@UseServerRuntime(CayenneProjects.MAP_TO_MANY_PROJECT)
-public class CayenneContextMapRelationshipIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    private TableHelper tMapToMany;
-    private TableHelper tMapToManyTarget;
-
-    @Before
-    public void setUp() throws Exception {
-        tMapToMany = new TableHelper(dbHelper, "ID_MAP_TO_MANY");
-        tMapToMany.setColumns("ID");
-
-        tMapToManyTarget = new TableHelper(dbHelper, "ID_MAP_TO_MANY_TARGET");
-        tMapToManyTarget.setColumns("ID", "MAP_TO_MANY_ID");
-    }
-
-    private void createTwoMapToManysWithTargetsDataSet() throws Exception {
-        tMapToMany.insert(1).insert(2);
-        tMapToManyTarget.insert(1, 1).insert(2, 1).insert(3, 1).insert(4, 2);
-    }
-
-    @Test
-    public void testReadToMany() throws Exception {
-        createTwoMapToManysWithTargetsDataSet();
-
-        ObjectId id = ObjectId.of("IdMapToMany", IdMapToMany.ID_PK_COLUMN, 1);
-        ClientIdMapToMany o1 = (ClientIdMapToMany) Cayenne.objectForQuery(
-                context,
-                new ObjectIdQuery(id));
-
-        Map<Object, ClientIdMapToManyTarget> targets = o1.getTargets();
-
-        assertTrue(((ValueHolder) targets).isFault());
-
-        assertNotNull(targets);
-        assertEquals(3, targets.size());
-        assertNotNull(targets.get(1));
-        assertNotNull(targets.get(2));
-        assertNotNull(targets.get(3));
-    }
-
-    @Test
-    public void testAddToMany() throws Exception {
-        createTwoMapToManysWithTargetsDataSet();
-
-        ObjectId id = ObjectId.of("IdMapToMany", IdMapToMany.ID_PK_COLUMN, 1);
-        ClientIdMapToMany o1 = (ClientIdMapToMany) Cayenne.objectForQuery(
-                context,
-                new ObjectIdQuery(id));
-
-        Map<Object, ClientIdMapToManyTarget> targets = o1.getTargets();
-        assertNotNull(targets);
-        assertEquals(3, targets.size());
-
-        ClientIdMapToManyTarget newTarget = o1.getObjectContext().newObject(
-                ClientIdMapToManyTarget.class);
-
-        o1.addToTargets(newTarget);
-        assertEquals(4, targets.size());
-        assertSame(o1, newTarget.getMapToMany());
-
-        o1.getObjectContext().commitChanges();
-
-        o1.getObjectContext().performGenericQuery(new RefreshQuery());
-        assertEquals(4, o1.getTargets().size());
-
-        int newId = Cayenne.intPKForObject(newTarget);
-        assertSame(newTarget, o1.getTargets().get(newId));
-
-        assertEquals(PersistenceState.COMMITTED, o1.getPersistenceState());
-        assertEquals(PersistenceState.COMMITTED, newTarget.getPersistenceState());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMeaningfulPKIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMeaningfulPKIT.java
deleted file mode 100644
index 40b236dbf..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMeaningfulPKIT.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.query.SortOrder;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.meaningful_pk.ClientMeaningfulPk;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-
-@UseServerRuntime(CayenneProjects.MEANINGFUL_PK_PROJECT)
-public class CayenneContextMeaningfulPKIT extends ClientCase {
-
-    @Inject
-    private CayenneContext clientContext;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    private TableHelper tMeaningfulPK;
-
-    @Before
-    public void setUp() throws Exception {
-        tMeaningfulPK = new TableHelper(dbHelper, "MEANINGFUL_PK");
-        tMeaningfulPK.setColumns("PK");
-    }
-
-    private void deleteAndCreateTwoMeaningfulPKsDataSet() throws Exception {
-        tMeaningfulPK.deleteAll();
-        tMeaningfulPK.insert("A");
-        tMeaningfulPK.insert("B");
-    }
-
-    @Test
-    public void testMeaningfulPK() throws Exception {
-        deleteAndCreateTwoMeaningfulPKsDataSet();
-
-        List<?> results = ObjectSelect.query(ClientMeaningfulPk.class)
-                .orderBy(ClientMeaningfulPk.PK.desc())
-                .select(clientContext);
-        assertEquals(2, results.size());
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMergeHandlerIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMergeHandlerIT.java
deleted file mode 100644
index 4606df475..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextMergeHandlerIT.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.graph.GraphEvent;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Mockito.mock;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextMergeHandlerIT extends ClientCase {
-
-    @Inject
-    protected CayenneContext context;
-
-    @Test
-    public void testShouldProcessEvent() {
-
-        CayenneContextMergeHandler handler = new CayenneContextMergeHandler(context);
-
-        // 1. Our context initiated the sync:
-        // src == channel && postedBy == context
-        GraphEvent e1 = new GraphEvent(context.getChannel(), context, null);
-        assertFalse(handler.shouldProcessEvent(e1));
-
-        // 2. Another context initiated the sync:
-        // postedBy != context && source == channel
-        GraphEvent e2 = new GraphEvent(context.getChannel(), mock(ObjectContext.class), null);
-        assertTrue(handler.shouldProcessEvent(e2));
-
-        // 2.1 Another object initiated the sync:
-        // postedBy != context && source == channel
-        GraphEvent e21 = new GraphEvent(context.getChannel(), new Object(), null);
-        assertTrue(handler.shouldProcessEvent(e21));
-
-        // 3. Another channel initiated the sync:
-        // postedBy == ? && source != channel
-        GraphEvent e3 = new GraphEvent(new MockDataChannel(), new Object(), null);
-        assertFalse(handler.shouldProcessEvent(e3));
-
-        // 4. inactive
-        GraphEvent e4 = new GraphEvent(context.getChannel(), mock(ObjectContext.class), null);
-        handler.active = false;
-        assertFalse(handler.shouldProcessEvent(e4));
-    }
-
-    @Test
-    public void testNodePropertyChanged() {
-
-        ClientMtTable1 o1 = context.newObject(ClientMtTable1.class);
-
-        CayenneContextMergeHandler handler = new CayenneContextMergeHandler(context);
-
-        assertNull(o1.getGlobalAttribute1Direct());
-
-        handler.nodePropertyChanged(o1.getObjectId(), ClientMtTable1.GLOBAL_ATTRIBUTE1.getName(), null, "abc");
-        assertEquals("abc", o1.getGlobalAttribute1Direct());
-
-        handler.nodePropertyChanged(o1.getObjectId(), ClientMtTable1.GLOBAL_ATTRIBUTE1.getName(), "abc", "xyz");
-
-        assertEquals("xyz", o1.getGlobalAttribute1Direct());
-
-        // block if old value is different
-        handler.nodePropertyChanged(o1.getObjectId(), ClientMtTable1.GLOBAL_ATTRIBUTE1.getName(), "123", "mnk");
-
-        assertEquals("xyz", o1.getGlobalAttribute1Direct());
-
-        handler.nodePropertyChanged(o1.getObjectId(), ClientMtTable1.GLOBAL_ATTRIBUTE1.getName(), "xyz", null);
-
-        assertNull(o1.getGlobalAttribute1Direct());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextNamedQueryCachingIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextNamedQueryCachingIT.java
deleted file mode 100644
index c0d39f879..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextNamedQueryCachingIT.java
+++ /dev/null
@@ -1,133 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.MappedSelect;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.unit.di.DataChannelInterceptor;
-import org.apache.cayenne.unit.di.UnitTestClosure;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotSame;
-import static org.junit.Assert.assertSame;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextNamedQueryCachingIT extends ClientCase {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private CayenneContext context;
-
-    @Inject(ClientCase.ROP_CLIENT_KEY)
-    private DataChannelInterceptor clientServerInterceptor;
-
-    private TableHelper tMtTable1;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-    }
-
-    protected void createThreeMtTable1sDataSet() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable1.insert(2, "g2", "s2");
-        tMtTable1.insert(3, "g3", "s3");
-    }
-
-    @Test
-    public void testLocalCache() throws Exception {
-        createThreeMtTable1sDataSet();
-
-        final MappedSelect q1 = MappedSelect.query("MtQueryWithLocalCache");
-
-        final List<?> result1 = context.performQuery(q1);
-        assertEquals(3, result1.size());
-
-        clientServerInterceptor.runWithQueriesBlocked(new UnitTestClosure() {
-
-            public void execute() {
-                List<?> result2 = context.performQuery(q1);
-                assertSame(result1, result2);
-            }
-        });
-
-        // refresh
-        q1.forceNoCache();
-        List<?> result3 = context.performQuery(q1);
-        assertNotSame(result1, result3);
-        assertEquals(3, result3.size());
-    }
-
-    @Test
-    public void testLocalCacheParameterized() throws Exception {
-        createThreeMtTable1sDataSet();
-
-        final MappedSelect q1 = MappedSelect.query("ParameterizedMtQueryWithLocalCache").param("g", "g1");
-        final MappedSelect q2 = MappedSelect.query("ParameterizedMtQueryWithLocalCache").param("g", "g2");
-
-        final List<?> result1 = context.performQuery(q1);
-        assertEquals(1, result1.size());
-
-        clientServerInterceptor.runWithQueriesBlocked(new UnitTestClosure() {
-
-            public void execute() {
-                List<?> result2 = context.performQuery(q1);
-                assertSame(result1, result2);
-            }
-        });
-        
-        final List<?> result3 = context.performQuery(q2);
-        assertNotSame(result1, result3);
-        assertEquals(1, result3.size());
-
-        clientServerInterceptor.runWithQueriesBlocked(new UnitTestClosure() {
-
-            public void execute() {
-                List<?> result4 = context.performQuery(q2);
-                assertSame(result3, result4);
-
-                List<?> result5 = context.performQuery(q1);
-                assertSame(result1, result5);
-            }
-        });
-    
-    }
-
-    @Test
-    public void testParameterizedMappedToEJBQLQueries() throws Exception {
-        
-        createThreeMtTable1sDataSet();
-
-        List<?> r1 = context.performQuery(MappedSelect.query("ParameterizedEJBQLMtQuery").param("g", "g1"));
-        assertEquals(1, r1.size());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextPaginatedListCachingIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextPaginatedListCachingIT.java
deleted file mode 100644
index d63ac95be..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextPaginatedListCachingIT.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextPaginatedListCachingIT extends ClientCase {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private CayenneContext context;
-
-    private TableHelper tMtTable1;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-    }
-
-    private void createSevenMtTable1sDataSet() throws Exception {
-        for (int i = 1; i <= 7; i++) {
-            tMtTable1.insert(i, "g" + i, "s" + i);
-        }
-    }
-
-    @Test
-    public void testLocalCache() throws Exception {
-        createSevenMtTable1sDataSet();
-
-        List<ClientMtTable1> result1 = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-                .pageSize(3)
-                .localCache()
-                .select(context);
-        assertEquals(7, result1.size());
-
-        // ensure we can resolve all objects without a failure...
-        for (ClientMtTable1 x : result1) {
-            x.getGlobalAttribute1();
-        }
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextPrimitiveIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextPrimitiveIT.java
deleted file mode 100644
index efb0e2441..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextPrimitiveIT.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.query.SortOrder;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.table_primitives.ClientTablePrimitives;
-import org.apache.cayenne.testdo.table_primitives.TablePrimitives;
-import org.apache.cayenne.unit.UnitDbAdapter;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.sql.Types;
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
-
-@UseServerRuntime(CayenneProjects.TABLE_PRIMITIVES_PROJECT)
-public class CayenneContextPrimitiveIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-    
-    @Inject
-    private UnitDbAdapter accessStackAdapter;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    private TableHelper tTablePrimitives;
-
-    @Before
-    public void setUp() throws Exception {
-        int bool = accessStackAdapter.supportsBoolean() ? Types.BOOLEAN : Types.INTEGER;
-        
-        tTablePrimitives = new TableHelper(dbHelper, "TABLE_PRIMITIVES");
-        tTablePrimitives.setColumns("ID", "BOOLEAN_COLUMN", "INT_COLUMN").setColumnTypes(
-                Types.INTEGER,
-                bool,
-                Types.INTEGER);
-    }
-
-    private void createTwoPrimitivesDataSet() throws Exception {
-        tTablePrimitives.insert(1, accessStackAdapter.supportsBoolean() ? true : 1, 0);
-        tTablePrimitives.insert(2, accessStackAdapter.supportsBoolean() ? false : 0, 5);
-    }
-
-    @Test
-    public void testSelectPrimitives() throws Exception {
-        createTwoPrimitivesDataSet();
-
-        List<ClientTablePrimitives> results = ObjectSelect.query(ClientTablePrimitives.class)
-                .orderBy("db:" + TablePrimitives.ID_PK_COLUMN, SortOrder.ASCENDING)
-                .select(context);
-        assertTrue(results.get(0).isBooleanColumn());
-        assertFalse(results.get(1).isBooleanColumn());
-
-        assertEquals(0, results.get(0).getIntColumn());
-        assertEquals(5, results.get(1).getIntColumn());
-    }
-
-    @Test
-    public void testCommitChangesPrimitives() throws Exception {
-
-        ClientTablePrimitives object = context.newObject(ClientTablePrimitives.class);
-
-        object.setBooleanColumn(true);
-        object.setIntColumn(3);
-
-        context.commitChanges();
-
-        assertTrue(tTablePrimitives.getBoolean("BOOLEAN_COLUMN"));
-        assertEquals(3, tTablePrimitives.getInt("INT_COLUMN"));
-
-        object.setBooleanColumn(false);
-        object.setIntColumn(8);
-        context.commitChanges();
-
-        assertFalse(tTablePrimitives.getBoolean("BOOLEAN_COLUMN"));
-        assertEquals(8, tTablePrimitives.getInt("INT_COLUMN"));
-    }
-
-    @Test
-    public void testCommitEmptyChangesPrimitives() throws Exception {
-
-        ClientTablePrimitives object = context.newObject(ClientTablePrimitives.class);
-
-        context.commitChanges();
-
-        assertFalse(tTablePrimitives.getBoolean("BOOLEAN_COLUMN"));
-        assertEquals(0, tTablePrimitives.getInt("INT_COLUMN"));
-
-        object.setBooleanColumn(true);
-        object.setIntColumn(8);
-        context.commitChanges();
-
-        assertTrue(tTablePrimitives.getBoolean("BOOLEAN_COLUMN"));
-        assertEquals(8, tTablePrimitives.getInt("INT_COLUMN"));
-    }
-
-    @Test
-    public void testSelectEmptyPrimitives() throws Exception {
-        tTablePrimitives.insert(1, accessStackAdapter.supportsBoolean() ? true : 1, null);
-
-        ClientTablePrimitives object = ObjectSelect.query(ClientTablePrimitives.class).selectFirst(context);
-
-        assertTrue(object.isBooleanColumn());
-        assertEquals(0, object.getIntColumn());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextReflexiveIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextReflexiveIT.java
deleted file mode 100644
index 29ab9e02f..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextReflexiveIT.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.access.ClientServerChannel;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.reflect.LifecycleCallbackRegistry;
-import org.apache.cayenne.testdo.reflexive.ClientReflexive;
-import org.apache.cayenne.testdo.reflexive.Reflexive;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-@UseServerRuntime(CayenneProjects.REFLEXIVE_PROJECT)
-public class CayenneContextReflexiveIT extends ClientCase {
-
-    @Inject
-    private CayenneContext clientContext;
-
-    @Inject
-    private ClientServerChannel clientServerChannel;
-
-    @Test
-    public void testCAY830() throws Exception {
-
-        // an exception was triggered within POST_LOAD callback
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        try {
-            callbackRegistry.addListener(Reflexive.class, new LifecycleListener() {
-
-                public void postLoad(Object entity) {
-                }
-
-                public void postPersist(Object entity) {
-                }
-
-                public void postRemove(Object entity) {
-                }
-
-                public void postUpdate(Object entity) {
-                }
-
-                public void postAdd(Object entity) {
-                }
-
-                public void preRemove(Object entity) {
-                }
-
-                public void preUpdate(Object entity) {
-                }
-
-                public void prePersist(Object entity) {
-                }
-            });
-
-            ClientReflexive o1 = clientContext.newObject(ClientReflexive.class);
-            o1.setName("parent");
-
-            ClientReflexive o2 = clientContext.newObject(ClientReflexive.class);
-            o2.setName("child");
-            o2.setToParent(o1);
-            clientContext.commitChanges();
-
-            clientContext.deleteObjects(o1);
-            clientContext.deleteObjects(o2);
-            clientContext.commitChanges();
-            // per CAY-830 an exception is thrown here
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextRefreshQueryIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextRefreshQueryIT.java
deleted file mode 100644
index a37860be2..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextRefreshQueryIT.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.RefreshQuery;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextRefreshQueryIT extends ClientCase {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private CayenneContext context;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-    }
-
-    private void createM1AndTwoM2sDataSet() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable2.insert(1, 1, "g1").insert(2, 1, "g1");
-    }
-
-    private void delete1M2DataSet() throws Exception {
-        tMtTable2.delete().where("TABLE2_ID", 1).execute();
-    }
-
-    @Test
-    public void testRefreshToMany() throws Exception {
-
-        createM1AndTwoM2sDataSet();
-
-        ClientMtTable1 a = Cayenne.objectForPK(context, ClientMtTable1.class, 1);
-        assertEquals(2, a.getTable2Array().size());
-
-        delete1M2DataSet();
-
-        RefreshQuery refresh = new RefreshQuery(a);
-        context.performGenericQuery(refresh);
-        assertEquals(PersistenceState.HOLLOW, a.getPersistenceState());
-        assertEquals(1, a.getTable2Array().size());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextRelationshipsIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextRelationshipsIT.java
deleted file mode 100644
index 46ceafaf7..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextRelationshipsIT.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.access.DataContext;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.MtTable1;
-import org.apache.cayenne.testdo.mt.MtTable2;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertSame;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextRelationshipsIT extends ClientCase {
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject
-    private CayenneContext context;
-
-    @Inject
-    private DataContext serverContext;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-    }
-
-    @Test
-    public void testLostUncommittedToOneModifications_Client() throws Exception {
-
-        tMtTable1.insert(1, "G1", "S1");
-        tMtTable1.insert(2, "G2", "S2");
-        tMtTable2.insert(33, 1, "GX");
-
-        ClientMtTable2 o = Cayenne.objectForPK(context, ClientMtTable2.class, 33);
-
-        ClientMtTable1 r2 = Cayenne.objectForPK(context, ClientMtTable1.class, 2);
-        ClientMtTable1 r1 = o.getTable1();
-
-        o.setTable1(r2);
-
-        assertSame(r2, o.getTable1());
-
-        // see CAY-1757 - this used to reset our changes
-        assertFalse(r1.getTable2Array().contains(o));
-        assertSame(r2, o.getTable1());
-    }
-
-    @Test
-    public void testLostUncommittedToOneModifications_Server() throws Exception {
-
-        tMtTable1.insert(1, "G1", "S1");
-        tMtTable1.insert(2, "G2", "S2");
-        tMtTable2.insert(33, 1, "GX");
-
-        MtTable2 o = Cayenne.objectForPK(serverContext, MtTable2.class, 33);
-
-        MtTable1 r2 = Cayenne.objectForPK(serverContext, MtTable1.class, 2);
-        MtTable1 r1 = o.getTable1();
-
-        o.setTable1(r2);
-
-        assertSame(r2, o.getTable1());
-
-        assertFalse(r1.getTable2Array().contains(o));
-        assertSame(r2, o.getTable1());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextSQLTemplateIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextSQLTemplateIT.java
deleted file mode 100644
index 8cc7c8483..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextSQLTemplateIT.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.SQLTemplate;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNull;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextSQLTemplateIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Test
-    public void testObjectRoot() throws Exception {
-
-        assertNull(Cayenne.objectForPK(context, ClientMtTable1.class, 1));
-        context.performGenericQuery(new SQLTemplate(
-                ClientMtTable1.class,
-                "insert into MT_TABLE1 "
-                        + "(TABLE1_ID, GLOBAL_ATTRIBUTE1, SERVER_ATTRIBUTE1) "
-                        + "values (1, 'g1', 's1')"));
-
-        assertNotNull(Cayenne.objectForPK(context, ClientMtTable1.class, 1));
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextServerDiffsIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextServerDiffsIT.java
deleted file mode 100644
index 2257c4cfc..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextServerDiffsIT.java
+++ /dev/null
@@ -1,163 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.access.ClientServerChannel;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.map.LifecycleEvent;
-import org.apache.cayenne.reflect.LifecycleCallbackRegistry;
-import org.apache.cayenne.remote.ClientChannelServerDiffsListener1;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.MtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNull;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextServerDiffsIT extends ClientCase {
-
-    @Inject
-    private ClientServerChannel clientServerChannel;
-
-    @Inject
-    private CayenneContext context;
-
-    @Test
-    public void testReturnDiffInPrePersist() {
-
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        try {
-
-            callbackRegistry.addListener(
-                    LifecycleEvent.POST_ADD,
-                    MtTable1.class,
-                    new ClientChannelServerDiffsListener1(),
-                    "prePersist");
-
-            ClientMtTable1 o = context.newObject(ClientMtTable1.class);
-            o.setServerAttribute1("YY");
-            context.commitChanges();
-
-            assertFalse(o.getObjectId().isTemporary());
-            assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-            assertEquals("XXX", o.getGlobalAttribute1());
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-
-    @Test
-    public void testReturnDiffInPreUpdate() {
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        try {
-
-            callbackRegistry.addListener(
-                    LifecycleEvent.PRE_UPDATE,
-                    MtTable1.class,
-                    new ClientChannelServerDiffsListener1(),
-                    "preUpdate");
-
-            ClientMtTable1 o = context.newObject(ClientMtTable1.class);
-            o.setServerAttribute1("YY");
-            context.commitChanges();
-
-            assertNull(o.getGlobalAttribute1());
-
-            o.setServerAttribute1("XX");
-            context.commitChanges();
-
-            assertFalse(o.getObjectId().isTemporary());
-            assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-            assertEquals("111", o.getGlobalAttribute1());
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-
-    @Test
-    public void testReturnDiffClientArcChanges() {
-
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        try {
-            callbackRegistry.addListener(
-                    LifecycleEvent.POST_ADD,
-                    MtTable1.class,
-                    new ClientChannelServerDiffsListener1(),
-                    "prePersist");
-
-            ClientMtTable1 o = context.newObject(ClientMtTable1.class);
-            ClientMtTable2 o1 = context.newObject(ClientMtTable2.class);
-            o.addToTable2Array(o1);
-            context.commitChanges();
-
-            assertFalse(o.getObjectId().isTemporary());
-            assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-            assertEquals("XXX", o.getGlobalAttribute1());
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-
-    @Test
-    public void testReturnDiffServerArcChanges() {
-
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        try {
-            callbackRegistry.addListener(
-                    LifecycleEvent.POST_ADD,
-                    MtTable1.class,
-                    new ClientChannelServerDiffsListener1(),
-                    "prePersistAddRelationship");
-
-            ClientMtTable1 o = context.newObject(ClientMtTable1.class);
-            ClientMtTable2 o1 = context.newObject(ClientMtTable2.class);
-            o.addToTable2Array(o1);
-            context.commitChanges();
-
-            assertFalse(o.getObjectId().isTemporary());
-            assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-            assertEquals(2, o.getTable2Array().size());
-
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextValidationIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextValidationIT.java
deleted file mode 100644
index d2442fbdf..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextValidationIT.java
+++ /dev/null
@@ -1,86 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.apache.cayenne.validation.ValidationException;
-import org.junit.Test;
-
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
-import static org.junit.Assert.fail;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextValidationIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Test
-    public void testValidate() throws Exception {
-
-        ClientMtTable1 o1 = context.newObject(ClientMtTable1.class);
-        o1.setGlobalAttribute1("G1");
-        o1.resetValidation(false);
-
-        // this one is not validating
-        ClientMtTable2 o2 = context.newObject(ClientMtTable2.class);
-        o2.setTable1(o1);
-
-        context.commitChanges();
-        assertTrue(o1.isValidatedForInsert());
-        assertFalse(o1.isValidatedForDelete());
-        assertFalse(o1.isValidatedForUpdate());
-
-        o1.resetValidation(false);
-        o1.setGlobalAttribute1("G2");
-
-        context.commitChanges();
-        assertFalse(o1.isValidatedForInsert());
-        assertFalse(o1.isValidatedForDelete());
-        assertTrue(o1.isValidatedForUpdate());
-
-        o1.resetValidation(false);
-        context.deleteObjects(o1);
-        context.deleteObjects(o2);
-
-        context.commitChanges();
-        assertFalse(o1.isValidatedForInsert());
-        assertTrue(o1.isValidatedForDelete());
-        assertFalse(o1.isValidatedForUpdate());
-
-        ClientMtTable1 o11 = context.newObject(ClientMtTable1.class);
-        o11.setGlobalAttribute1("G1");
-        o11.resetValidation(true);
-
-        try {
-            context.commitChanges();
-            fail("Validation failure must have prevented commit");
-        }
-        catch (ValidationException e) {
-            // expected
-        }
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextWithDataContextIT.java b/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextWithDataContextIT.java
deleted file mode 100644
index 6ffb5b27d..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/CayenneContextWithDataContextIT.java
+++ /dev/null
@@ -1,465 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import java.sql.Types;
-import java.util.List;
-
-import org.apache.cayenne.access.ClientServerChannel;
-import org.apache.cayenne.access.DataContext;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.map.LifecycleEvent;
-import org.apache.cayenne.query.ObjectIdQuery;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.reflect.LifecycleCallbackRegistry;
-import org.apache.cayenne.remote.RemoteIncrementalFaultList;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.test.parallel.ParallelTestContainer;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.MtTable1;
-import org.apache.cayenne.unit.di.DataChannelInterceptor;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.*;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class CayenneContextWithDataContextIT extends ClientCase {
-
-    @Inject
-    private CayenneContext clientContext;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    @Inject(ClientCase.ROP_CLIENT_KEY)
-    private DataChannelInterceptor clientServerInterceptor;
-
-    @Inject
-    private ClientServerChannel clientServerChannel;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE").setColumnTypes(
-                Types.INTEGER, Types.INTEGER, Types.VARCHAR);
-    }
-
-    private void createTwoMtTable1sAnd2sDataSet() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable1.insert(2, "g2", "s2");
-
-        tMtTable2.insert(1, 1, "g1");
-        tMtTable2.insert(2, 1, "g2");
-    }
-
-    private void createEightMtTable1s() throws Exception {
-        for (int i = 1; i <= 8; i++) {
-            tMtTable1.insert(i, "g" + i, "s" + i);
-        }
-    }
-
-    @Test
-    public void testLocalCacheStaysLocal() {
-        ObjectSelect<ClientMtTable1> query = ObjectSelect.query(ClientMtTable1.class).localCache();
-        List<?> results = query.select(clientContext);
-
-        assertSame(results, clientContext.getQueryCache().get(query.getMetaData(clientContext.getEntityResolver())));
-    }
-
-    @Test
-    public void testAddToList() {
-
-        ClientMtTable1 t1 = clientContext.newObject(ClientMtTable1.class);
-        ClientMtTable2 t2 = clientContext.newObject(ClientMtTable2.class);
-
-        t1.addToTable2Array(t2);
-        assertEquals(1, t1.getTable2Array().size());
-        assertSame(t1, t2.getTable1());
-
-        // do it again to make sure action can handle series of changes
-        ClientMtTable1 t3 = clientContext.newObject(ClientMtTable1.class);
-        ClientMtTable2 t4 = clientContext.newObject(ClientMtTable2.class);
-
-        t3.addToTable2Array(t4);
-        assertEquals(1, t3.getTable2Array().size());
-        assertSame(t3, t4.getTable1());
-    }
-
-    @Test
-    public void testSetValueHolder() {
-
-        ClientMtTable1 t1 = clientContext.newObject(ClientMtTable1.class);
-        ClientMtTable2 t2 = clientContext.newObject(ClientMtTable2.class);
-
-        t2.setTable1(t1);
-        assertEquals(1, t1.getTable2Array().size());
-        assertSame(t1, t2.getTable1());
-    }
-
-    @Test
-    public void testPostAddCallback() {
-
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        final boolean[] flag = new boolean[1];
-
-        try {
-            callbackRegistry.addListener(MtTable1.class, new LifecycleListener() {
-
-                public void postLoad(Object entity) {
-                }
-
-                public void postPersist(Object entity) {
-                }
-
-                public void postRemove(Object entity) {
-                }
-
-                public void postUpdate(Object entity) {
-                }
-
-                public void postAdd(Object entity) {
-                    flag[0] = true;
-                }
-
-                public void preRemove(Object entity) {
-                }
-
-                public void preUpdate(Object entity) {
-                }
-
-                public void prePersist(Object entity) {
-                }
-            });
-
-            clientContext.newObject(ClientMtTable1.class);
-
-            assertFalse(flag[0]);
-            clientContext.commitChanges();
-            assertTrue(flag[0]);
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-
-    @Test
-    public void testPostAddOnObjectCallback() throws Exception {
-
-        final DataContext serverContext = (DataContext) clientServerChannel.getParentChannel();
-
-        LifecycleCallbackRegistry callbackRegistry = serverContext
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        try {
-            callbackRegistry.addCallback(
-                    LifecycleEvent.POST_ADD,
-                    MtTable1.class,
-                    "prePersistMethod");
-
-            final Persistent clientObject = clientContext.newObject(ClientMtTable1.class);
-            clientContext.commitChanges();
-
-        new ParallelTestContainer() {
-
-            @Override
-            protected void assertResult() {
-            	// find peer
-            	MtTable1 peer = (MtTable1) serverContext.getGraphManager().getNode(clientObject.getObjectId());
-            	assertNotNull(peer);
-            	assertTrue(peer.isPrePersisted());
-            }
-        }.runTest(1000);
-
-
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-
-    @Test
-    public void testPreRemoveCallback() {
-
-        // an exception was triggered within POST_LOAD callback
-        LifecycleCallbackRegistry callbackRegistry = clientServerChannel
-                .getEntityResolver()
-                .getCallbackRegistry();
-
-        final boolean[] flag = new boolean[1];
-
-        try {
-            callbackRegistry.addListener(MtTable1.class, new LifecycleListener() {
-
-                public void postLoad(Object entity) {
-                }
-
-                public void postPersist(Object entity) {
-                }
-
-                public void postRemove(Object entity) {
-                }
-
-                public void postUpdate(Object entity) {
-                }
-
-                public void postAdd(Object entity) {
-                }
-
-                public void preRemove(Object entity) {
-                    flag[0] = true;
-                }
-
-                public void preUpdate(Object entity) {
-                }
-
-                public void prePersist(Object entity) {
-                }
-            });
-
-            ClientMtTable1 object = clientContext.newObject(ClientMtTable1.class);
-
-            assertFalse(flag[0]);
-            clientContext.commitChanges();
-            assertFalse(flag[0]);
-
-            clientContext.deleteObjects(object);
-            clientContext.commitChanges();
-            assertTrue(flag[0]);
-        }
-        finally {
-            callbackRegistry.clear();
-        }
-    }
-
-    @Test
-    public void testRollbackChanges() {
-
-        ClientMtTable1 o = clientContext.newObject(ClientMtTable1.class);
-        o.setGlobalAttribute1("1");
-        clientContext.commitChanges();
-
-        assertEquals("1", o.getGlobalAttribute1());
-        o.setGlobalAttribute1("2");
-        assertEquals("2", o.getGlobalAttribute1());
-        clientContext.rollbackChanges();
-
-        assertEquals("1", o.getGlobalAttribute1());
-        assertTrue(clientContext.modifiedObjects().isEmpty());
-    }
-
-    @Test
-    public void testCreateFault() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-
-        ObjectId id = ObjectId.of("MtTable1", MtTable1.TABLE1_ID_PK_COLUMN, 1);
-
-        Object fault = clientContext.createFault(id);
-        assertTrue(fault instanceof ClientMtTable1);
-
-        ClientMtTable1 o = (ClientMtTable1) fault;
-        assertEquals(PersistenceState.HOLLOW, o.getPersistenceState());
-        assertSame(clientContext, o.getObjectContext());
-        assertNull(o.getGlobalAttribute1Direct());
-
-        // make sure we haven't tripped the fault yet
-        assertEquals(PersistenceState.HOLLOW, o.getPersistenceState());
-
-        // try tripping fault
-        assertEquals("g1", o.getGlobalAttribute1());
-        assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-    }
-
-    @Test
-    public void testCreateBadFault() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-
-        ObjectId id = ObjectId.of("MtTable1", MtTable1.TABLE1_ID_PK_COLUMN, 2);
-
-        Object fault = clientContext.createFault(id);
-        assertTrue(fault instanceof ClientMtTable1);
-
-        ClientMtTable1 o = (ClientMtTable1) fault;
-
-        // try tripping fault
-        try {
-            o.getGlobalAttribute1();
-            fail("resolving bad fault should've thrown");
-        }
-        catch (FaultFailureException e) {
-            // expected
-        }
-    }
-
-    @Test
-    public void testPrefetchingToOne() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        final ObjectId prefetchedId = ObjectId.of(
-                "MtTable1",
-                MtTable1.TABLE1_ID_PK_COLUMN,
-                1);
-
-        ObjectSelect<ClientMtTable2> q = ObjectSelect.query(ClientMtTable2.class)
-                .orderBy(ClientMtTable2.GLOBAL_ATTRIBUTE.asc())
-                .prefetch(ClientMtTable2.TABLE1.disjoint());
-
-        final List<ClientMtTable2> results = q.select(clientContext);
-
-        clientServerInterceptor.runWithQueriesBlocked(() -> {
-            assertEquals(2, results.size());
-
-            for (ClientMtTable2 o : results) {
-                assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-                assertSame(clientContext, o.getObjectContext());
-
-                ClientMtTable1 o1 = o.getTable1();
-                assertNotNull(o1);
-                assertEquals(PersistenceState.COMMITTED, o1.getPersistenceState());
-                assertSame(clientContext, o1.getObjectContext());
-                assertEquals(prefetchedId, o1.getObjectId());
-            }
-        });
-    }
-
-    @Test
-    public void testPrefetchingToOneNull() throws Exception {
-        tMtTable2.insert(15, null, "g3");
-
-        ObjectSelect<ClientMtTable2> q = ObjectSelect.query(ClientMtTable2.class)
-                .prefetch(ClientMtTable2.TABLE1.disjoint());
-
-        final List<ClientMtTable2> results = q.select(clientContext);
-
-        clientServerInterceptor.runWithQueriesBlocked(() -> {
-            assertEquals(1, results.size());
-
-            ClientMtTable2 o = results.get(0);
-            assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-            assertSame(clientContext, o.getObjectContext());
-
-            assertNull(o.getTable1());
-        });
-    }
-
-    @Test
-    public void testPrefetchingToMany() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-                .prefetch(ClientMtTable1.TABLE2ARRAY.joint());
-
-        final List<ClientMtTable1> results = q.select(clientContext);
-
-        clientServerInterceptor.runWithQueriesBlocked(() -> {
-
-            ClientMtTable1 o1 = results.get(0);
-            assertEquals(PersistenceState.COMMITTED, o1.getPersistenceState());
-            assertSame(clientContext, o1.getObjectContext());
-
-            List<ClientMtTable2> children1 = o1.getTable2Array();
-
-            assertEquals(2, children1.size());
-            for (ClientMtTable2 o : children1) {
-                assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-                assertSame(clientContext, o.getObjectContext());
-
-                // TODO: fixme... reverse relationship is not connected and will
-                // cause a fetch
-                // assertEquals(o1, o.getTable1());
-            }
-        });
-    }
-
-    @Test
-    public void testPerformPaginatedQuery() throws Exception {
-        createEightMtTable1s();
-
-        ObjectSelect<ClientMtTable1> query = ObjectSelect.query(ClientMtTable1.class)
-                .pageSize(5);
-        List<ClientMtTable1> objects = query.select(clientContext);
-        assertNotNull(objects);
-        assertTrue(objects instanceof RemoteIncrementalFaultList);
-    }
-
-    @Test
-    public void testPrefetchingToManyEmpty() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-        
-        ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-                .prefetch(ClientMtTable1.TABLE2ARRAY.joint());
-
-        final List<ClientMtTable1> results = q.select(clientContext);
-
-        clientServerInterceptor.runWithQueriesBlocked(() -> {
-            ClientMtTable1 o2 = results.get(1);
-            assertEquals(PersistenceState.COMMITTED, o2.getPersistenceState());
-            assertSame(clientContext, o2.getObjectContext());
-
-            List<ClientMtTable2> children2 = o2.getTable2Array();
-            assertFalse(((ValueHolder) children2).isFault());
-            assertEquals(0, children2.size());
-        });
-    }
-
-    @Test
-    public void testOIDQueryInterception() {
-
-        final ClientMtTable1 o = clientContext.newObject(ClientMtTable1.class);
-        o.setGlobalAttribute1("aaa");
-
-        // fetch new
-        final ObjectIdQuery q1 = new ObjectIdQuery(o.getObjectId(), false, ObjectIdQuery.CACHE);
-
-        clientServerInterceptor.runWithQueriesBlocked(() -> {
-            List<?> objects = clientContext.performQuery(q1);
-            assertEquals(1, objects.size());
-            assertSame(o, objects.get(0));
-        });
-
-        clientContext.commitChanges();
-
-        // fetch committed
-        final ObjectIdQuery q2 = new ObjectIdQuery(o.getObjectId(), false, ObjectIdQuery.CACHE);
-
-        clientServerInterceptor.runWithQueriesBlocked(() -> {
-            List<?> objects = clientContext.performQuery(q2);
-            assertEquals(1, objects.size());
-            assertSame(o, objects.get(0));
-        });
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/DataRowTest.java b/cayenne-client/src/test/java/org/apache/cayenne/DataRowTest.java
deleted file mode 100644
index 188714253..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/DataRowTest.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotSame;
-
-public class DataRowTest {
-
-    @Test
-    public void testHessianSerializability() throws Exception {
-        DataRow s1 = new DataRow(10);
-        s1.put("a", "b");
-
-        DataRow s2 = (DataRow) HessianUtil.cloneViaServerClientSerialization(s1, new EntityResolver());
-
-        assertNotSame(s1, s2);
-        assertEquals(s1, s2);
-        assertEquals(s1.getVersion(), s2.getVersion());
-        assertEquals(s1.getReplacesVersion(), s2.getReplacesVersion());
-
-        // at the moment there are no serializers that can go from client to
-        // server.
-        // DataRow s3 = (DataRow) HessianUtil.cloneViaClientServerSerialization(
-        // s1,
-        // new EntityResolver());
-        //
-        // assertNotSame(s1, s3);
-        // assertEquals(s1, s3);
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/NestedCayenneContextIT.java b/cayenne-client/src/test/java/org/apache/cayenne/NestedCayenneContextIT.java
deleted file mode 100644
index e746e93b9..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/NestedCayenneContextIT.java
+++ /dev/null
@@ -1,680 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.configuration.rop.client.ClientRuntime;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.graph.ArcId;
-import org.apache.cayenne.graph.GraphChangeHandler;
-import org.apache.cayenne.graph.GraphDiff;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.query.SelectById;
-import org.apache.cayenne.query.SortOrder;
-import org.apache.cayenne.remote.RemoteCayenneCase;
-import org.apache.cayenne.remote.service.LocalConnection;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.unit.di.DataChannelInterceptor;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-import org.junit.runners.Parameterized.Parameters;
-
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-
-/**
- * Tests nested object contexts
- */
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-@RunWith(value = Parameterized.class)
-public class NestedCayenneContextIT extends RemoteCayenneCase {
-
-	@Inject
-	private ClientRuntime runtime;
-
-	@Inject
-	private DataChannelInterceptor queryInterceptor;
-
-	@Parameters
-	public static Collection<Object[]> data() {
-		return Arrays.asList(new Object[][] {
-				{ LocalConnection.HESSIAN_SERIALIZATION },
-				{ LocalConnection.JAVA_SERIALIZATION },
-				{ LocalConnection.NO_SERIALIZATION }, });
-	}
-
-	public NestedCayenneContextIT(int serializationPolicy) {
-		super.serializationPolicy = serializationPolicy;
-	}
-
-	@Test
-	public void testChannels() {
-		ObjectContext child = runtime.newContext(clientContext);
-
-		assertNotNull(child);
-		assertSame(clientContext, child.getChannel());
-
-		// second level of nesting
-		ObjectContext grandchild = runtime.newContext(child);
-
-		assertNotNull(grandchild);
-		assertSame(child, grandchild.getChannel());
-	}
-
-	@Test
-	public void testSelect() {
-		ObjectContext child = runtime.newContext(clientContext);
-
-		ClientMtTable1 committed = clientContext.newObject(ClientMtTable1.class);
-		ClientMtTable1 deleted = clientContext.newObject(ClientMtTable1.class);
-		ClientMtTable1 modified = clientContext.newObject(ClientMtTable1.class);
-
-		clientContext.commitChanges();
-		int modifiedid = Cayenne.intPKForObject(modified);
-
-		// test how different object states appear in the child on select
-
-		clientContext.deleteObjects(deleted);
-		modified.setGlobalAttribute1("a");
-
-		ClientMtTable1 _new = clientContext.newObject(ClientMtTable1.class);
-
-		assertEquals(PersistenceState.COMMITTED, committed.getPersistenceState());
-		assertEquals(PersistenceState.MODIFIED, modified.getPersistenceState());
-		assertEquals(PersistenceState.DELETED, deleted.getPersistenceState());
-		assertEquals(PersistenceState.NEW, _new.getPersistenceState());
-
-		List<ClientMtTable1> objects = ObjectSelect.query(ClientMtTable1.class).select(child);
-		assertEquals("All but NEW object must have been included", 3, objects.size());
-
-		for (ClientMtTable1 next : objects) {
-			assertEquals(PersistenceState.COMMITTED, next.getPersistenceState());
-
-			int id = Cayenne.intPKForObject(next);
-			if (id == modifiedid) {
-				assertEquals("a", next.getGlobalAttribute1());
-			}
-		}
-	}
-
-	@Test
-	public void testPrefetchingToOne() {
-		final ClientMtTable1 mt11 = clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		ClientMtTable2 mt21 = clientContext.newObject(ClientMtTable2.class);
-		ClientMtTable2 mt22 = clientContext.newObject(ClientMtTable2.class);
-
-		mt21.setTable1(mt11);
-		mt22.setTable1(mt11);
-
-		clientContext.commitChanges();
-
-		final ObjectContext child = runtime.newContext(clientContext);
-
-		final List<ClientMtTable2> results = ObjectSelect.query(ClientMtTable2.class)
-				.prefetch(ClientMtTable2.TABLE1.joint())
-				.select(child);
-
-		queryInterceptor.runWithQueriesBlocked(() -> {
-			assertEquals(2, results.size());
-			for (ClientMtTable2 o : results) {
-				assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-				assertSame(child, o.getObjectContext());
-
-				ClientMtTable1 o1 = o.getTable1();
-				assertNotNull(o1);
-				assertEquals(PersistenceState.COMMITTED, o1.getPersistenceState());
-				assertSame(child, o1.getObjectContext());
-				assertEquals(mt11.getObjectId(), o1.getObjectId());
-			}
-		});
-	}
-
-	@Test
-	public void testPrefetchingToMany() {
-		ClientMtTable1 mt11 = clientContext.newObject(ClientMtTable1.class);
-		mt11.setGlobalAttribute1("1");
-
-		ClientMtTable1 mt12 = clientContext.newObject(ClientMtTable1.class);
-		mt12.setGlobalAttribute1("2");
-
-		ClientMtTable2 mt21 = clientContext.newObject(ClientMtTable2.class);
-		ClientMtTable2 mt22 = clientContext.newObject(ClientMtTable2.class);
-
-		mt21.setTable1(mt11);
-		mt22.setTable1(mt11);
-
-		clientContext.commitChanges();
-
-		final ObjectContext child = runtime.newContext(clientContext);
-
-		final List<ClientMtTable1> results = ObjectSelect.query(ClientMtTable1.class)
-				.prefetch(ClientMtTable1.TABLE2ARRAY.joint())
-				.orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-				.select(child);
-
-		queryInterceptor.runWithQueriesBlocked(() -> {
-			ClientMtTable1 o1 = results.get(0);
-			assertEquals(PersistenceState.COMMITTED, o1.getPersistenceState());
-			assertSame(child, o1.getObjectContext());
-
-			List<ClientMtTable2> children1 = o1.getTable2Array();
-
-			assertEquals(2, children1.size());
-			for (ClientMtTable2 o : children1) {
-				assertEquals(PersistenceState.COMMITTED, o.getPersistenceState());
-				assertSame(child, o.getObjectContext());
-				assertEquals(o1, o.getTable1());
-			}
-
-			ClientMtTable1 o2 = results.get(1);
-			assertEquals(PersistenceState.COMMITTED, o2.getPersistenceState());
-			assertSame(child, o2.getObjectContext());
-
-			List<?> children2 = o2.getTable2Array();
-
-			assertEquals(0, children2.size());
-		});
-	}
-
-	@Test
-	public void testDeleteNew() {
-		ObjectContext child = runtime.newContext(clientContext);
-
-		ClientMtTable1 a = clientContext.newObject(ClientMtTable1.class);
-		clientContext.commitChanges();
-
-		ClientMtTable2 p = child.newObject(ClientMtTable2.class);
-		ClientMtTable1 aChild = (ClientMtTable1) Cayenne.objectForPK(child, a.getObjectId());
-		p.setGlobalAttribute("X");
-		aChild.addToTable2Array(p);
-
-		child.commitChangesToParent();
-
-		child.deleteObjects(p);
-		aChild.removeFromTable2Array(p);
-
-		child.commitChangesToParent();
-	}
-
-	/**
-	 * A test case for CAY-698 bug.
-	 */
-	@Test
-	public void testNullifyToOne() {
-		ClientMtTable1 a = clientContext.newObject(ClientMtTable1.class);
-		ClientMtTable2 b = clientContext.newObject(ClientMtTable2.class);
-		a.addToTable2Array(b);
-
-		clientContext.commitChanges();
-
-		ObjectContext child = runtime.newContext(clientContext);
-		ObjectContext childPeer = runtime.newContext(clientContext);
-
-		ClientMtTable2 childP1 = SelectById.query(ClientMtTable2.class, b.getObjectId()).selectOne(child);
-
-		// trigger object creation in the peer nested DC
-		Cayenne.objectForPK(childPeer, b.getObjectId());
-		childP1.setTable1(null);
-
-		queryInterceptor.runWithQueriesBlocked(() -> {
-			child.commitChangesToParent();
-			assertEquals(PersistenceState.COMMITTED, childP1.getPersistenceState());
-
-			ClientMtTable2 parentP1 = (ClientMtTable2) clientContext.getGraphManager().getNode(childP1.getObjectId());
-
-			assertNotNull(parentP1);
-			assertEquals(PersistenceState.MODIFIED, parentP1.getPersistenceState());
-			assertNull(parentP1.getTable1());
-
-			// check that arc changes got recorded in the parent context
-			GraphDiff diffs = clientContext.internalGraphManager().getDiffs();
-			final int[] arcDiffs = new int[1];
-
-			diffs.apply(new GraphChangeHandler() {
-				@Override
-				public void arcCreated(Object nodeId, Object targetNodeId, ArcId arcId) {
-					arcDiffs[0]++;
-				}
-
-				@Override
-				public void arcDeleted(Object nodeId, Object targetNodeId, ArcId arcId) {
-					arcDiffs[0]--;
-				}
-
-				@Override
-				public void nodeCreated(Object nodeId) {
-				}
-
-				@Override
-				public void nodeIdChanged(Object nodeId, Object newId) {
-				}
-
-				@Override
-				public void nodePropertyChanged(Object nodeId,
-						String property, Object oldValue, Object newValue) {
-				}
-
-				@Override
-				public void nodeRemoved(Object nodeId) {
-				}
-			});
-
-			assertEquals(-2, arcDiffs[0]);
-		});
-	}
-
-	@Test
-	public void testCommitChangesToParent() {
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.commitChanges();
-
-		final ObjectContext child = runtime.newContext(clientContext);
-
-		List<ClientMtTable1> objects = ObjectSelect.query(ClientMtTable1.class).select(child);
-
-		assertEquals(4, objects.size());
-
-		final ClientMtTable1 childNew = child.newObject(ClientMtTable1.class);
-		childNew.setGlobalAttribute1("NNN");
-
-		final ClientMtTable1 childModified = objects.get(0);
-		childModified.setGlobalAttribute1("MMM");
-
-		final ClientMtTable1 childCommitted = objects.get(1);
-
-		final ClientMtTable1 childHollow = objects.get(3);
-		child.invalidateObjects(childHollow);
-
-		queryInterceptor.runWithQueriesBlocked(() -> {
-			child.commitChangesToParent();
-
-			// * all modified child objects must be in committed state now
-			// * all modifications should be propagated to the parent
-			// * no actual commit should occur.
-
-			assertEquals(PersistenceState.COMMITTED, childNew.getPersistenceState());
-			assertEquals(PersistenceState.COMMITTED, childModified.getPersistenceState());
-			assertEquals(PersistenceState.COMMITTED, childCommitted.getPersistenceState());
-			assertEquals(PersistenceState.HOLLOW, childHollow.getPersistenceState());
-
-			ClientMtTable1 parentNew = (ClientMtTable1) clientContext
-					.getGraphManager().getNode(childNew.getObjectId());
-			final ClientMtTable1 parentModified = (ClientMtTable1) clientContext
-					.getGraphManager().getNode(childModified.getObjectId());
-			ClientMtTable1 parentCommitted = (ClientMtTable1) clientContext
-					.getGraphManager()
-					.getNode(childCommitted.getObjectId());
-			ClientMtTable1 parentHollow = (ClientMtTable1) clientContext
-					.getGraphManager().getNode(childHollow.getObjectId());
-
-			assertNotNull(parentNew);
-			assertEquals(PersistenceState.NEW, parentNew.getPersistenceState());
-			assertEquals("NNN", parentNew.getGlobalAttribute1());
-
-			assertNotNull(parentModified);
-			assertEquals(PersistenceState.MODIFIED, parentModified.getPersistenceState());
-			assertEquals("MMM", parentModified.getGlobalAttribute1());
-
-			assertNotNull(parentCommitted);
-			assertEquals(PersistenceState.COMMITTED, parentCommitted.getPersistenceState());
-
-			assertNotNull(parentHollow);
-
-			// check that arc changes got recorded in the parent context
-			GraphDiff diffs = clientContext.internalGraphManager().getDiffs();
-
-			final int[] modifiedProperties = new int[1];
-
-			diffs.apply(new GraphChangeHandler() {
-
-				@Override
-				public void arcCreated(Object nodeId, Object targetNodeId, ArcId arcId) {
-				}
-
-				@Override
-				public void arcDeleted(Object nodeId, Object targetNodeId, ArcId arcId) {
-				}
-
-				@Override
-				public void nodeCreated(Object nodeId) {
-				}
-
-				@Override
-				public void nodeIdChanged(Object nodeId, Object newId) {
-				}
-
-				@Override
-				public void nodePropertyChanged(Object nodeId, String property, Object oldValue, Object newValue) {
-					if (nodeId.equals(parentModified.getObjectId())) {
-						modifiedProperties[0]++;
-					}
-				}
-
-				@Override
-				public void nodeRemoved(Object nodeId) {
-				}
-			});
-
-			assertEquals(1, modifiedProperties[0]);
-		});
-	}
-
-	@Test
-	public void testCommitChangesToParentDeleted() {
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.commitChanges();
-
-		ObjectContext child = runtime.newContext(clientContext);
-
-		// make sure we fetch in predictable order
-		List<ClientMtTable1> objects = ObjectSelect.query(ClientMtTable1.class).select(child);
-
-		assertEquals(4, objects.size());
-
-		// delete AND modify
-		ClientMtTable1 childDeleted = objects.get(2);
-		child.deleteObjects(childDeleted);
-		childDeleted.setGlobalAttribute1("DDD");
-
-		// don't block queries - on delete Cayenne may need to resolve delete
-		// rules via fetch
-		child.commitChangesToParent();
-
-		// * all modified child objects must be in committed state now
-		// * all modifications should be propagated to the parent
-		// * no actual commit should occur.
-
-		assertEquals(PersistenceState.TRANSIENT, childDeleted.getPersistenceState());
-
-		ClientMtTable1 parentDeleted = (ClientMtTable1) clientContext.getGraphManager()
-				.getNode(childDeleted.getObjectId());
-
-		assertNotNull(parentDeleted);
-		assertEquals(PersistenceState.DELETED,
-				parentDeleted.getPersistenceState());
-		assertEquals("DDD", parentDeleted.getGlobalAttribute1());
-	}
-
-	@Test
-	public void testCommitChanges() {
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.newObject(ClientMtTable1.class);
-		clientContext.commitChanges();
-
-		ObjectContext child = runtime.newContext(clientContext);
-
-		// make sure we fetch in predictable order
-		List<ClientMtTable1> objects = ObjectSelect.query(ClientMtTable1.class).select(child);
-
-		assertEquals(4, objects.size());
-
-		ClientMtTable1 childNew = child.newObject(ClientMtTable1.class);
-		childNew.setGlobalAttribute1("NNN");
-
-		ClientMtTable1 childModified = objects.get(0);
-		childModified.setGlobalAttribute1("MMM");
-
-		ClientMtTable1 childCommitted = objects.get(1);
-
-		// delete AND modify
-		ClientMtTable1 childDeleted = objects.get(2);
-		child.deleteObjects(childDeleted);
-		childDeleted.setGlobalAttribute1("DDD");
-
-		ClientMtTable1 childHollow = objects.get(3);
-		child.invalidateObjects(childHollow);
-
-		child.commitChanges();
-
-		assertEquals(PersistenceState.COMMITTED, childNew.getPersistenceState());
-		assertEquals(PersistenceState.COMMITTED, childModified.getPersistenceState());
-		assertEquals(PersistenceState.COMMITTED, childCommitted.getPersistenceState());
-		assertEquals(PersistenceState.TRANSIENT, childDeleted.getPersistenceState());
-		assertEquals(PersistenceState.HOLLOW, childHollow.getPersistenceState());
-
-		ClientMtTable1 parentNew = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(childNew.getObjectId());
-		ClientMtTable1 parentModified = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(childModified.getObjectId());
-		ClientMtTable1 parentCommitted = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(childCommitted.getObjectId());
-		ClientMtTable1 parentDeleted = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(childDeleted.getObjectId());
-		ClientMtTable1 parentHollow = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(childHollow.getObjectId());
-
-		assertNotNull(parentNew);
-		assertEquals(PersistenceState.COMMITTED, parentNew.getPersistenceState());
-		assertEquals("NNN", parentNew.getGlobalAttribute1());
-
-		assertNotNull(parentModified);
-		assertEquals(PersistenceState.COMMITTED, parentModified.getPersistenceState());
-		assertEquals("MMM", parentModified.getGlobalAttribute1());
-
-		assertNull("Deleted object should not be registered.", parentDeleted);
-
-		assertNotNull(parentCommitted);
-		assertEquals(PersistenceState.COMMITTED, parentCommitted.getPersistenceState());
-
-		assertNotNull(parentHollow);
-	}
-
-	@Test
-	public void testAddRemove() {
-		ObjectContext child = runtime.newContext(clientContext);
-
-		ClientMtTable1 a = child.newObject(ClientMtTable1.class);
-		a.setGlobalAttribute1("X");
-		child.commitChanges();
-
-		ClientMtTable2 p1 = child.newObject(ClientMtTable2.class);
-		p1.setGlobalAttribute("P1");
-		a.addToTable2Array(p1);
-
-		ClientMtTable2 p2 = child.newObject(ClientMtTable2.class);
-		p2.setGlobalAttribute("P2");
-		a.addToTable2Array(p2);
-
-		a.removeFromTable2Array(p2);
-
-		// this causes an error on commit
-		child.deleteObjects(p2);
-
-		child.commitChangesToParent();
-
-	}
-
-	@Test
-	public void testChangeRel() {
-		ObjectContext child = runtime.newContext(clientContext);
-
-		ClientMtTable1 a = child.newObject(ClientMtTable1.class);
-		ClientMtTable2 b = child.newObject(ClientMtTable2.class);
-		child.commitChanges();
-
-		assertEquals(PersistenceState.COMMITTED, a.getPersistenceState());
-
-		a.addToTable2Array(b);
-		assertEquals(PersistenceState.MODIFIED, a.getPersistenceState());
-
-		child.commitChangesToParent();
-		ClientMtTable1 parentA = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(a.getObjectId());
-		assertEquals(PersistenceState.COMMITTED, a.getPersistenceState());
-		assertEquals(PersistenceState.MODIFIED, parentA.getPersistenceState());
-		assertEquals(1, parentA.getTable2Array().size());
-
-		clientContext.commitChanges();
-		assertEquals(PersistenceState.COMMITTED, parentA.getPersistenceState());
-
-		a.removeFromTable2Array(b);
-		assertEquals(PersistenceState.MODIFIED, a.getPersistenceState());
-
-		child.commitChangesToParent();
-		assertEquals(PersistenceState.COMMITTED, a.getPersistenceState());
-		assertEquals(PersistenceState.MODIFIED, parentA.getPersistenceState());
-		assertEquals(0, parentA.getTable2Array().size());
-	}
-
-	@Test
-	public void testCAY1183()  {
-		ClientMtTable1 parentMt = clientContext.newObject(ClientMtTable1.class);
-		clientContext.commitChanges();
-
-		ObjectContext child = runtime.newContext(clientContext);
-		ClientMtTable1 childMt = (ClientMtTable1) Cayenne.objectForPK(child,
-				parentMt.getObjectId());
-		childMt.setGlobalAttribute1("1183");
-		ClientMtTable2 childMt2 = child.newObject(ClientMtTable2.class);
-		childMt2.setGlobalAttribute("1183");
-		childMt2.setTable1(childMt);
-
-		child.commitChangesToParent();
-
-		// fetching other relationship... this fails per CAY-1183
-		childMt2.getTable3();
-	}
-
-	/**
-	 * CAY1714
-	 */
-	@Test
-	public void testQueriesOnTemporaryObject() {
-		ObjectContext clientContext = runtime.newContext(this.clientContext);
-		ClientMtTable1 parentMt = clientContext.newObject(ClientMtTable1.class);
-
-		ObjectContext childContext = runtime.newContext(clientContext);
-		ClientMtTable1 childMt = (ClientMtTable1) Cayenne.objectForPK(childContext, parentMt.getObjectId());
-		childMt.setGlobalAttribute1("1183");
-		ClientMtTable2 childMt2 = childContext.newObject(ClientMtTable2.class);
-		childMt2.setGlobalAttribute("1183");
-		childMt2.setTable1(childMt);
-
-		childContext.commitChangesToParent();
-
-		assertNull(childMt2.getTable3());
-	}
-
-	@Test
-	public void testCAY1194() {
-		ClientMtTable1 parentMt = clientContext.newObject(ClientMtTable1.class);
-		ObjectContext child = runtime.newContext(clientContext);
-
-		ClientMtTable2 childMt2 = child.newObject(ClientMtTable2.class);
-		childMt2.setGlobalAttribute("222");
-
-		ClientMtTable1 localParentMt = child.localObject(parentMt);
-		assertEquals(0, parentMt.getTable2Array().size());
-		assertEquals(0, localParentMt.getTable2Array().size());
-
-		childMt2.setTable1(localParentMt);
-
-		assertEquals(0, parentMt.getTable2Array().size());
-		assertEquals(1, localParentMt.getTable2Array().size());
-
-		assertEquals(localParentMt.getTable2Array().get(0).getObjectContext(),
-				child);
-
-		child.commitChangesToParent();
-		assertEquals(1, parentMt.getTable2Array().size());
-		assertEquals(parentMt.getTable2Array().get(0).getObjectContext(),
-				clientContext);
-	}
-
-	@Test
-	public void testCommitChangesToParentOneToMany() {
-		ObjectContext child = runtime.newContext(clientContext);
-
-		ClientMtTable1 master = child.newObject(ClientMtTable1.class);
-		ClientMtTable2 dep = child.newObject(ClientMtTable2.class);
-		master.addToTable2Array(dep);
-
-		child.commitChangesToParent();
-
-		ClientMtTable1 masterParent = (ClientMtTable1) clientContext
-				.getGraphManager().getNode(master.getObjectId());
-		ClientMtTable2 depParent = (ClientMtTable2) clientContext
-				.getGraphManager().getNode(dep.getObjectId());
-
-		assertNotNull(masterParent);
-		assertNotNull(depParent);
-
-		assertSame(masterParent, depParent.getTable1());
-		assertTrue(masterParent.getTable2Array().contains(depParent));
-
-		// check that arc changes got recorded in the parent context
-		GraphDiff diffs = clientContext.internalGraphManager().getDiffs();
-
-		final int[] arcDiffs = new int[1];
-		final int[] newNodes = new int[1];
-
-		diffs.apply(new GraphChangeHandler() {
-			@Override
-			public void arcCreated(Object nodeId, Object targetNodeId, ArcId arcId) {
-				arcDiffs[0]++;
-			}
-
-			@Override
-			public void arcDeleted(Object nodeId, Object targetNodeId, ArcId arcId) {
-				arcDiffs[0]--;
-			}
-
-			@Override
-			public void nodeCreated(Object nodeId) {
-				newNodes[0]++;
-			}
-
-			@Override
-			public void nodeIdChanged(Object nodeId, Object newId) {
-			}
-
-			@Override
-			public void nodePropertyChanged(Object nodeId, String property, Object oldValue, Object newValue) {
-			}
-
-			@Override
-			public void nodeRemoved(Object nodeId) {
-				newNodes[0]--;
-			}
-		});
-
-		assertEquals(2, newNodes[0]);
-		assertEquals(2, arcDiffs[0]);
-	}
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/NestedCayenneContextTooneIT.java b/cayenne-client/src/test/java/org/apache/cayenne/NestedCayenneContextTooneIT.java
deleted file mode 100644
index c63eff710..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/NestedCayenneContextTooneIT.java
+++ /dev/null
@@ -1,222 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.List;
-
-import org.apache.cayenne.configuration.rop.client.ClientRuntime;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.graph.ArcId;
-import org.apache.cayenne.graph.GraphChangeHandler;
-import org.apache.cayenne.graph.GraphDiff;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.remote.RemoteCayenneCase;
-import org.apache.cayenne.remote.service.LocalConnection;
-import org.apache.cayenne.testdo.toone.ClientTooneDep;
-import org.apache.cayenne.testdo.toone.ClientTooneMaster;
-import org.apache.cayenne.unit.di.DataChannelInterceptor;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertSame;
-
-@UseServerRuntime(CayenneProjects.TOONE_PROJECT)
-@RunWith(value = Parameterized.class)
-public class NestedCayenneContextTooneIT extends RemoteCayenneCase {
-
-    @Inject
-    private ClientRuntime runtime;
-
-    @Inject
-    private DataChannelInterceptor queryInterceptor;
-
-    @Parameterized.Parameters
-    public static Collection<Object[]> data() {
-        return Arrays.asList(new Object[][]{
-                {LocalConnection.HESSIAN_SERIALIZATION},
-                {LocalConnection.JAVA_SERIALIZATION},
-                {LocalConnection.NO_SERIALIZATION},});
-    }
-
-    public NestedCayenneContextTooneIT(int serializationPolicy) {
-        super.serializationPolicy = serializationPolicy;
-    }
-
-    /*
- * was added for CAY-1636
- */
-    @Test
-    public void testCAY1636() throws Exception {
-
-        ClientTooneMaster A = clientContext
-                .newObject(ClientTooneMaster.class);
-        clientContext.commitChanges();
-
-        ClientTooneDep B = clientContext.newObject(ClientTooneDep.class);
-        A.setToDependent(B);
-        clientContext.commitChanges();
-
-        ObjectContext child = runtime.newContext(clientContext);
-
-        ObjectSelect<ClientTooneMaster> query = ObjectSelect.query(ClientTooneMaster.class);
-        List<ClientTooneMaster> objects = child.select(query);
-
-        assertEquals(1, objects.size());
-
-        ClientTooneMaster childDeleted = objects.get(0);
-
-        child.deleteObjects(childDeleted);
-
-        child.commitChangesToParent();
-
-        ClientTooneMaster parentDeleted = (ClientTooneMaster) clientContext
-                .getGraphManager().getNode(childDeleted.getObjectId());
-
-        assertNotNull(parentDeleted);
-        assertEquals(PersistenceState.DELETED,
-                parentDeleted.getPersistenceState());
-
-        clientContext.commitChanges();
-
-        ObjectSelect<ClientTooneMaster> query2 = ObjectSelect.query(ClientTooneMaster.class);
-        List<ClientTooneMaster> objects2 = child.select(query2);
-
-        assertEquals(0, objects2.size());
-
-    }
-
-    @Test
-    public void testCAY1636_2() throws Exception {
-
-        ClientTooneMaster A = clientContext
-                .newObject(ClientTooneMaster.class);
-        clientContext.commitChanges();
-
-        ClientTooneDep B = clientContext.newObject(ClientTooneDep.class);
-        A.setToDependent(B);
-        clientContext.commitChanges();
-
-        ObjectContext child = runtime.newContext(clientContext);
-
-        ObjectSelect<ClientTooneDep> queryB = ObjectSelect.query(ClientTooneDep.class);
-        List<?> objectsB = child.performQuery(queryB);
-
-        assertEquals(1, objectsB.size());
-
-        ClientTooneDep childBDeleted = (ClientTooneDep) objectsB.get(0);
-        child.deleteObjects(childBDeleted);
-
-        ObjectSelect<ClientTooneMaster> query = ObjectSelect.query(ClientTooneMaster.class);
-        List<ClientTooneMaster> objects = child.select(query);
-
-        assertEquals(1, objects.size());
-
-        ClientTooneMaster childDeleted = objects.get(0);
-
-        child.deleteObjects(childDeleted);
-
-        child.commitChangesToParent();
-
-        ClientTooneMaster parentDeleted = (ClientTooneMaster) clientContext
-                .getGraphManager().getNode(childDeleted.getObjectId());
-
-        assertNotNull(parentDeleted);
-        assertEquals(PersistenceState.DELETED,
-                parentDeleted.getPersistenceState());
-
-        clientContext.commitChanges();
-
-        ObjectSelect<ClientTooneMaster> query2 = ObjectSelect.query(ClientTooneMaster.class);
-        List<ClientTooneMaster> objects2 = child.select(query2);
-
-        assertEquals(0, objects2.size());
-
-    }
-
-    @Test
-    public void testCommitChangesToParentOneToOne() throws Exception {
-        ObjectContext child = runtime.newContext(clientContext);
-
-        ClientTooneMaster master = child.newObject(ClientTooneMaster.class);
-        ClientTooneDep dep = child.newObject(ClientTooneDep.class);
-        master.setToDependent(dep);
-
-        child.commitChangesToParent();
-
-        ClientTooneMaster masterParent = (ClientTooneMaster) clientContext
-                .getGraphManager().getNode(master.getObjectId());
-        ClientTooneDep depParent = (ClientTooneDep) clientContext
-                .getGraphManager().getNode(dep.getObjectId());
-
-        assertNotNull(masterParent);
-        assertNotNull(depParent);
-
-        assertSame(masterParent, depParent.getToMaster());
-        assertSame(depParent, masterParent.getToDependent());
-
-        // check that arc changes got recorded in the parent context
-        GraphDiff diffs = clientContext.internalGraphManager().getDiffs();
-
-        final int[] arcDiffs = new int[1];
-        final int[] newNodes = new int[1];
-
-        diffs.apply(new GraphChangeHandler() {
-
-            @Override
-            public void arcCreated(Object nodeId, Object targetNodeId, ArcId arcId) {
-                arcDiffs[0]++;
-            }
-
-            @Override
-            public void arcDeleted(Object nodeId, Object targetNodeId, ArcId arcId) {
-                arcDiffs[0]--;
-            }
-
-            @Override
-            public void nodeCreated(Object nodeId) {
-                newNodes[0]++;
-            }
-
-            @Override
-            public void nodeIdChanged(Object nodeId, Object newId) {
-            }
-
-            @Override
-            public void nodePropertyChanged(Object nodeId, String property, Object oldValue, Object newValue) {
-            }
-
-            @Override
-            public void nodeRemoved(Object nodeId) {
-                newNodes[0]--;
-            }
-        });
-
-        assertEquals(2, newNodes[0]);
-        assertEquals(2, arcDiffs[0]);
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/ObjectContextChangeLogTest.java b/cayenne-client/src/test/java/org/apache/cayenne/ObjectContextChangeLogTest.java
deleted file mode 100644
index 453823337..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/ObjectContextChangeLogTest.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.graph.CompoundDiff;
-import org.apache.cayenne.graph.NodeCreateOperation;
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-
-public class ObjectContextChangeLogTest {
-
-    @Test
-    public void testGetDiffsSerializableWithHessian() throws Exception {
-        ObjectContextChangeLog recorder = new ObjectContextChangeLog();
-
-        // id must be a serializable object
-        recorder.addOperation(new NodeCreateOperation("id-string"));
-        CompoundDiff diff = (CompoundDiff) recorder.getDiffs();
-
-        Object clone = HessianUtil.cloneViaClientServerSerialization(diff, new EntityResolver());
-        assertNotNull(clone);
-        assertTrue(clone instanceof CompoundDiff);
-
-        CompoundDiff d1 = (CompoundDiff) clone;
-        assertEquals(1, d1.getDiffs().size());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/ObjectIdTest.java b/cayenne-client/src/test/java/org/apache/cayenne/ObjectIdTest.java
deleted file mode 100644
index a3b5e68cb..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/ObjectIdTest.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne;
-
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import java.util.Collections;
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotSame;
-import static org.junit.Assert.assertTrue;
-
-public class ObjectIdTest {
-
-    @Test
-    public void testHessianSerializabilityTemp() throws Exception {
-        ObjectId temp1 = ObjectId.of("e");
-
-        // make sure hashcode is resolved
-        int h = temp1.hashCode();
-        assertEquals(h, temp1.hashCode());
-        assertTrue(temp1.hashCode() != 0);
-
-        ObjectId temp2 = (ObjectId) HessianUtil.cloneViaClientServerSerialization(temp1, new EntityResolver());
-
-        // make sure hashCode is reset to 0
-        assertEquals(h, temp2.hashCode());
-
-        assertTrue(temp1.isTemporary());
-        assertNotSame(temp1, temp2);
-        assertEquals(temp1, temp2);
-    }
-
-    @Test
-    public void testHessianSerializabilityPerm() throws Exception {
-        ObjectId perm1 = ObjectId.of("e", "a", "b");
-
-        // make sure hashcode is resolved
-        int h = perm1.hashCode();
-        assertEquals(h, perm1.hashCode());
-        assertTrue(perm1.hashCode() != 0);
-
-        ObjectId perm2 = (ObjectId) HessianUtil.cloneViaClientServerSerialization(perm1, new EntityResolver());
-
-        assertEquals(h, perm2.hashCode());
-
-        assertFalse(perm2.isTemporary());
-        assertNotSame(perm1, perm2);
-        assertEquals(perm1, perm2);
-    }
-
-    @Test
-    public void testHessianSerializabilityPerm1() throws Exception {
-        // test serializing an id created with unmodifiable map
-
-        Map<String, Object> id = Collections.unmodifiableMap(Collections.singletonMap("a", "b"));
-        ObjectId perm1 = ObjectId.of("e", id);
-        ObjectId perm2 = (ObjectId) HessianUtil.cloneViaClientServerSerialization(perm1, new EntityResolver());
-
-        assertFalse(perm2.isTemporary());
-        assertNotSame(perm1, perm2);
-        assertEquals(perm1, perm2);
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/PersistentObjectInContextIT.java b/cayenne-client/src/test/java/org/apache/cayenne/PersistentObjectInContextIT.java
deleted file mode 100644
index f267ce705..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/PersistentObjectInContextIT.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne;
-
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectIdQuery;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.MtTable1;
-import org.apache.cayenne.testdo.mt.MtTable2;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.apache.cayenne.util.PersistentObjectHolder;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class PersistentObjectInContextIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-    }
-
-    private void createTwoMtTable1sAnd2sDataSet() throws Exception {
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable1.insert(2, "g2", "s2");
-
-        tMtTable2.insert(1, 1, "g1");
-        tMtTable2.insert(2, 1, "g2");
-    }
-
-    @Test
-    public void testResolveToManyReverseResolved() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectId gid = ObjectId.of(
-                "MtTable1",
-                MtTable1.TABLE1_ID_PK_COLUMN,
-                1);
-        ClientMtTable1 t1 = (ClientMtTable1) Cayenne.objectForQuery(
-                context,
-                new ObjectIdQuery(gid));
-
-        assertNotNull(t1);
-
-        List<ClientMtTable2> t2s = t1.getTable2Array();
-        assertEquals(2, t2s.size());
-
-        for (ClientMtTable2 t2 : t2s) {
-
-            PersistentObjectHolder holder = (PersistentObjectHolder) t2.getTable1Direct();
-            assertFalse(holder.isFault());
-            assertSame(t1, holder.getValue());
-        }
-    }
-
-    @Test
-    public void testToOneRelationship() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectId gid = ObjectId.of(
-                "MtTable2",
-                MtTable2.TABLE2_ID_PK_COLUMN,
-                1);
-        ClientMtTable2 mtTable21 = (ClientMtTable2) Cayenne.objectForQuery(
-                context,
-                new ObjectIdQuery(gid));
-
-        assertNotNull(mtTable21);
-
-        ClientMtTable1 mtTable1 = mtTable21.getTable1();
-        assertNotNull("To one relationship incorrectly resolved to null", mtTable1);
-        assertEquals("g1", mtTable1.getGlobalAttribute1());
-    }
-
-    @Test
-    public void testResolveToOneReverseResolved() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectId gid = ObjectId.of(
-                "MtTable2",
-                MtTable2.TABLE2_ID_PK_COLUMN,
-                1);
-        ClientMtTable2 mtTable21 = (ClientMtTable2) Cayenne.objectForQuery(
-                context,
-                new ObjectIdQuery(gid));
-
-        assertNotNull(mtTable21);
-
-        ClientMtTable1 mtTable1 = mtTable21.getTable1();
-        assertNotNull("To one relationship incorrectly resolved to null", mtTable1);
-
-        List<ClientMtTable2> list = mtTable1.getTable2Array();
-        assertNotNull(list);
-        assertTrue(list instanceof ValueHolder);
-
-        assertTrue(((ValueHolder) list).isFault());
-
-        // resolve it here...
-        assertEquals(2, list.size());
-        for (ClientMtTable2 t2 : list) {
-            PersistentObjectHolder holder = (PersistentObjectHolder) t2.getTable1Direct();
-            assertFalse(holder.isFault());
-            assertSame(mtTable1, holder.getValue());
-        }
-
-        assertEquals("g1", mtTable1.getGlobalAttribute1());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/access/ClientServerChannelIT.java b/cayenne-client/src/test/java/org/apache/cayenne/access/ClientServerChannelIT.java
deleted file mode 100644
index 1429de5a1..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/access/ClientServerChannelIT.java
+++ /dev/null
@@ -1,263 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.access;
-
-import java.util.List;
-
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.MockDataChannel;
-import org.apache.cayenne.ObjectContext;
-import org.apache.cayenne.ObjectId;
-import org.apache.cayenne.QueryResponse;
-import org.apache.cayenne.ValueHolder;
-import org.apache.cayenne.configuration.server.ServerRuntime;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.graph.GraphDiff;
-import org.apache.cayenne.graph.NodeCreateOperation;
-import org.apache.cayenne.log.JdbcEventLogger;
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.query.MockQuery;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.query.Query;
-import org.apache.cayenne.remote.QueryMessage;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable1Subclass1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.ClientMtTable3;
-import org.apache.cayenne.testdo.mt.MtTable1;
-import org.apache.cayenne.testdo.mt.MtTable3;
-import org.apache.cayenne.unit.di.DataChannelInterceptor;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.apache.cayenne.util.EqualsBuilder;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.*;
-import static org.mockito.Mockito.mock;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class ClientServerChannelIT extends ClientCase {
-
-	@Inject
-	protected DataContext serverContext;
-
-	@Inject
-	protected ClientServerChannel clientServerChannel;
-
-	@Inject
-	protected DBHelper dbHelper;
-
-	@Inject
-	protected DataChannelInterceptor queryInterceptor;
-
-	@Inject
-	protected JdbcEventLogger logger;
-
-	@Inject
-	private ServerRuntime runtime;
-
-	private TableHelper tMtTable1;
-	private TableHelper tMtTable2;
-	private TableHelper tMtTable3;
-
-	@Before
-	public void setUp() throws Exception {
-		tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-		tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-		tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-		tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-
-		tMtTable3 = new TableHelper(dbHelper, "MT_TABLE3");
-		tMtTable3.setColumns("TABLE3_ID", "BINARY_COLUMN", "CHAR_COLUMN", "INT_COLUMN");
-	}
-
-	private void createTwoMtTable1sAnd2sDataSet() throws Exception {
-
-		tMtTable1.insert(1, "g1", "s1");
-		tMtTable1.insert(2, "g2", "s2");
-
-		tMtTable2.insert(1, 1, "g1");
-		tMtTable2.insert(2, 1, "g2");
-	}
-
-	@Test
-	public void testGetEntityResolver() {
-		EntityResolver resolver = clientServerChannel.getEntityResolver();
-		assertNotNull(resolver);
-		assertNull(resolver.getObjEntity(ClientMtTable1.class));
-		assertNotNull(resolver.getClientEntityResolver().getObjEntity(ClientMtTable1.class));
-	}
-
-	@Test
-	public void testSynchronizeCommit() {
-
-		ObjectSelect<MtTable1> query = ObjectSelect.query(MtTable1.class);
-
-		// no changes...
-		clientServerChannel.onSync(serverContext, mock(GraphDiff.class), DataChannel.FLUSH_CASCADE_SYNC);
-
-		assertEquals(0, serverContext.performQuery(query).size());
-
-		// introduce changes
-		clientServerChannel.onSync(serverContext
-				, new NodeCreateOperation(ObjectId.of("MtTable1"))
-				, DataChannel.FLUSH_CASCADE_SYNC);
-
-		assertEquals(1, serverContext.performQuery(query).size());
-	}
-
-	@Test
-	public void testPerformQueryObjectIDInjection() throws Exception {
-		tMtTable1.insert(55, "g1", "s1");
-
-		Query query = ObjectSelect.query(MtTable1.class);
-		QueryResponse response = clientServerChannel.onQuery(null, query);
-
-		assertNotNull(response);
-
-		List<?> results = response.firstList();
-
-		assertNotNull(results);
-		assertEquals(1, results.size());
-
-		Object result = results.get(0);
-		assertTrue(result instanceof ClientMtTable1);
-		ClientMtTable1 clientObject = (ClientMtTable1) result;
-		assertNotNull(clientObject.getObjectId());
-
-		assertEquals(ObjectId.of("MtTable1", MtTable1.TABLE1_ID_PK_COLUMN, 55), clientObject.getObjectId());
-	}
-
-	@Test
-	public void testPerformQueryValuePropagation() throws Exception {
-
-		byte[] bytes = new byte[] { 1, 2, 3 };
-
-		tMtTable3.insert(1, bytes, "abc", 4);
-
-		Query query = ObjectSelect.query(MtTable3.class);
-		QueryResponse response = clientServerChannel.onQuery(null, query);
-
-		assertNotNull(response);
-
-		List<?> results = response.firstList();
-
-		assertNotNull(results);
-		assertEquals(1, results.size());
-
-		Object result = results.get(0);
-		assertTrue("Result is of wrong type: " + result, result instanceof ClientMtTable3);
-		ClientMtTable3 clientObject = (ClientMtTable3) result;
-
-		assertEquals("abc", clientObject.getCharColumn());
-		assertEquals(new Integer(4), clientObject.getIntColumn());
-		assertTrue(new EqualsBuilder().append(clientObject.getBinaryColumn(), bytes).isEquals());
-	}
-
-	@Test
-	public void testPerformQueryPropagationInheritance() throws Exception {
-
-		tMtTable1.insert(65, "sub1", "xyz");
-
-		ObjectSelect<ClientMtTable1> query = ObjectSelect.query(ClientMtTable1.class);
-		QueryResponse response = clientServerChannel.onQuery(null, query);
-
-		assertNotNull(response);
-
-		List<?> results = response.firstList();
-
-		assertNotNull(results);
-		assertEquals(1, results.size());
-
-		Object result = results.get(0);
-		assertTrue("Result is of wrong type: " + result, result instanceof ClientMtTable1Subclass1);
-		ClientMtTable1Subclass1 clientObject = (ClientMtTable1Subclass1) result;
-
-		assertEquals("sub1", clientObject.getGlobalAttribute1());
-	}
-
-	@Test
-	public void testOnQuery() {
-
-		final boolean[] genericDone = new boolean[1];
-		MockDataChannel parent = new MockDataChannel(new EntityResolver()) {
-
-			@Override
-			public QueryResponse onQuery(ObjectContext context, Query query) {
-				genericDone[0] = true;
-				return super.onQuery(context, query);
-			}
-		};
-		DataContext context = (DataContext) runtime.newContext(parent);
-
-		QueryMessage message = new QueryMessage(new MockQuery());
-		new ClientServerChannel(context).onQuery(null, message.getQuery());
-		assertTrue(genericDone[0]);
-	}
-
-	@Test
-	public void testOnQueryPrefetchingToMany() throws Exception {
-		createTwoMtTable1sAnd2sDataSet();
-
-		ObjectSelect<ClientMtTable1> query = ObjectSelect.query(ClientMtTable1.class)
-				.orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-				.prefetch(ClientMtTable1.TABLE2ARRAY.joint());
-
-		final List<?> results = clientServerChannel.onQuery(null, query).firstList();
-
-		queryInterceptor.runWithQueriesBlocked(() -> {
-			ClientMtTable1 o1 = (ClientMtTable1) results.get(0);
-			assertNull(o1.getObjectContext());
-
-			List<ClientMtTable2> children1 = o1.getTable2Array();
-
-			assertEquals(2, children1.size());
-			for (ClientMtTable2 o : children1) {
-				assertNull(o.getObjectContext());
-			}
-		});
-	}
-
-	@Test
-	public void testOnQueryPrefetchingToManyEmpty() throws Exception {
-		createTwoMtTable1sAnd2sDataSet();
-
-		ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class)
-				.orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-				.prefetch(ClientMtTable1.TABLE2ARRAY.joint());
-
-		final List<?> results = clientServerChannel.onQuery(null, q).firstList();
-
-		queryInterceptor.runWithQueriesBlocked(() -> {
-			ClientMtTable1 o2 = (ClientMtTable1) results.get(1);
-			assertNull(o2.getObjectContext());
-
-			List<?> children2 = o2.getTable2Array();
-			assertNotNull(children2);
-			assertFalse(((ValueHolder) children2).isFault());
-			assertEquals(0, children2.size());
-		});
-	}
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/access/ClientServerChannelQueryIT.java b/cayenne-client/src/test/java/org/apache/cayenne/access/ClientServerChannelQueryIT.java
deleted file mode 100644
index 5d26fb4ca..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/access/ClientServerChannelQueryIT.java
+++ /dev/null
@@ -1,241 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.access;
-
-import java.util.List;
-
-import org.apache.cayenne.ObjectContext;
-import org.apache.cayenne.ValueHolder;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.MappedSelect;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.testdo.mt.MtTable1;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.apache.cayenne.util.PersistentObjectHolder;
-import org.apache.cayenne.util.PersistentObjectList;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class ClientServerChannelQueryIT extends ClientCase {
-
-    @Inject(ClientCase.ROP_CLIENT_KEY)
-    protected ObjectContext context;
-
-    @Inject
-    private ClientServerChannel serverChannel;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-    }
-
-    protected void createSevenMtTable1sDataSet() throws Exception {
-
-        for (int i = 1; i <= 7; i++) {
-            tMtTable1.insert(i, "g" + i, "s" + i);
-        }
-    }
-
-    protected void createTwoMtTable1sAnd2sDataSet() throws Exception {
-
-        tMtTable1.insert(1, "g1", "s1");
-        tMtTable1.insert(2, "g2", "s2");
-
-        tMtTable2.insert(1, 1, "g1");
-        tMtTable2.insert(2, 1, "g2");
-    }
-
-    @SuppressWarnings("deprecation")
-    @Test
-    public void testPaginatedQueryServerCacheOverflow() throws Exception {
-        createSevenMtTable1sDataSet();
-
-        ObjectSelect<ClientMtTable1> query = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc())
-                .pageSize(3);
-
-        List<?> results = context.performQuery(query);
-
-        // read page 1
-        assertTrue(results.get(0) instanceof ClientMtTable1);
-
-        assertTrue(results.get(3) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testParameterizedMappedToEJBQLQueries() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        List<?> r1 = context.performQuery(MappedSelect.query("ParameterizedEJBQLMtQuery").param("g", "g1"));
-        assertEquals(1, r1.size());
-        assertTrue(r1.get(0) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testNamedQuery() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        List<?> results = context.performQuery(MappedSelect.query("AllMtTable1"));
-
-        assertEquals(2, results.size());
-        assertTrue(results.get(0) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testSelectQueryEntityNameRoot() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect q = ObjectSelect.query(MtTable1.class);
-        List<?> results = context.performQuery(q);
-
-        assertEquals(2, results.size());
-
-        assertTrue(results.get(0) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testSelectQueryClientClassRoot() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class);
-        List<?> results = context.performQuery(q);
-
-        assertEquals(2, results.size());
-        assertTrue(results.get(0) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testSelectQuerySimpleQualifier() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class)
-                .where(ClientMtTable1.GLOBAL_ATTRIBUTE1.eq("g1"));
-        List<?> results = context.performQuery(q);
-
-        assertEquals(1, results.size());
-
-        assertTrue(results.get(0) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testSelectQueryToManyRelationshipQualifier() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class)
-                .where(ClientMtTable1.TABLE2ARRAY.dot(ClientMtTable2.GLOBAL_ATTRIBUTE).eq("g1"));
-        List<?> results = context.performQuery(q);
-
-        assertEquals(1, results.size());
-        assertTrue(results.get(0) instanceof ClientMtTable1);
-    }
-
-    @Test
-    public void testSelectQueryOrdering() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect q = ObjectSelect.query(MtTable1.class)
-                .orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.asc());
-        List<?> results = context.performQuery(q);
-
-        assertEquals(2, results.size());
-
-        ClientMtTable1 o1 = (ClientMtTable1) results.get(0);
-        ClientMtTable1 o2 = (ClientMtTable1) results.get(1);
-        assertTrue(o1.getGlobalAttribute1().compareTo(o2.getGlobalAttribute1()) < 0);
-
-        // now run the same query with reverse ordering to check that the first ordering
-        // result wasn't coincidental.
-        q.getOrderings().clear();
-        q.orderBy(ClientMtTable1.GLOBAL_ATTRIBUTE1.desc());
-        List<?> results1 = context.performQuery(q);
-
-        assertEquals(2, results1.size());
-
-        ClientMtTable1 o3 = (ClientMtTable1) results1.get(0);
-        ClientMtTable1 o4 = (ClientMtTable1) results1.get(1);
-        assertTrue(o3.getGlobalAttribute1().compareTo(o4.getGlobalAttribute1()) > 0);
-    }
-
-    @Test
-    public void testSelectQueryPrefetchToOne() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect<ClientMtTable2> q = ObjectSelect.query(ClientMtTable2.class)
-                .where(ClientMtTable2.GLOBAL_ATTRIBUTE.eq("g1"))
-                .prefetch(ClientMtTable2.TABLE1.disjoint());
-        List<?> results = context.performQuery(q);
-
-        assertEquals(1, results.size());
-
-        ClientMtTable2 result = (ClientMtTable2) results.get(0);
-
-        ValueHolder holder = result.getTable1Direct();
-        assertNotNull(holder);
-        assertTrue(holder instanceof PersistentObjectHolder);
-        PersistentObjectHolder objectHolder = (PersistentObjectHolder) holder;
-        assertFalse(objectHolder.isFault());
-
-        ClientMtTable1 target = (ClientMtTable1) objectHolder.getValue();
-        assertNotNull(target);
-    }
-
-    @Test
-    public void testSelectQueryPrefetchToMany() throws Exception {
-        createTwoMtTable1sAnd2sDataSet();
-
-        ObjectSelect<ClientMtTable1> q = ObjectSelect.query(ClientMtTable1.class)
-                .where(ClientMtTable1.GLOBAL_ATTRIBUTE1.eq("g1"))
-                .prefetch(ClientMtTable1.TABLE2ARRAY.joint());
-        List<?> results = context.performQuery(q);
-
-        assertEquals(1, results.size());
-
-        ClientMtTable1 result = (ClientMtTable1) results.get(0);
-
-        List<?> holder = result.getTable2ArrayDirect();
-        assertNotNull(holder);
-        assertTrue(holder instanceof PersistentObjectList);
-        PersistentObjectList objectHolder = (PersistentObjectList) holder;
-        assertFalse(objectHolder.isFault());
-        assertEquals(2, objectHolder.size());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/access/types/EnumTest.java b/cayenne-client/src/test/java/org/apache/cayenne/access/types/EnumTest.java
deleted file mode 100644
index e13db5823..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/access/types/EnumTest.java
+++ /dev/null
@@ -1,113 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.access.types;
-
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.apache.cayenne.util.Util;
-import org.junit.Test;
-
-import java.io.Serializable;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertSame;
-
-/**
- * A test case checking Cayenne handling of 1.5 Enums.
- * 
- */
-public class EnumTest {
-
-    @Test
-    public void testSerializabilityWithHessianStandalone() throws Exception {
-        MockEnum before = MockEnum.a;
-
-        // test standalone
-        Object after = HessianUtil.cloneViaClientServerSerialization(
-                before,
-                new EntityResolver());
-        assertNotNull(after);
-        assertSame(before, after);
-    }
-
-    @Test
-    public void testSerializabilityWithHessianInTheMap() throws Exception {
-        // test in the Map
-        Map<String, MockEnum> map = new HashMap<>();
-        map.put("a", MockEnum.b);
-
-        Map after = (Map) HessianUtil.cloneViaClientServerSerialization(
-                (Serializable) map,
-                new EntityResolver());
-        assertNotNull(map);
-        assertSame(MockEnum.b, after.get("a"));
-
-    }
-
-    @Test
-    public void testSerializabilityWithHessianObjectProperty() throws Exception {
-        // test object property
-        MockEnumHolder object = new MockEnumHolder();
-        object.setMockEnum(MockEnum.b);
-
-        MockEnumHolder after = (MockEnumHolder) HessianUtil
-                .cloneViaClientServerSerialization(object, new EntityResolver());
-        assertNotNull(after);
-        assertSame(MockEnum.b, after.getMockEnum());
-    }
-
-    @Test
-    public void testSerializabilityWithHessianObjectPropertyInAList() throws Exception {
-
-        // test that Enum properties are serialized properly...
-
-        MockEnumHolder o1 = new MockEnumHolder();
-        o1.setMockEnum(MockEnum.b);
-
-        MockEnumHolder o2 = new MockEnumHolder();
-        o2.setMockEnum(MockEnum.c);
-
-        ArrayList<MockEnumHolder> l = new ArrayList<MockEnumHolder>();
-        l.add(o1);
-        l.add(o2);
-
-        ArrayList ld = (ArrayList) HessianUtil.cloneViaClientServerSerialization(
-                l,
-                new EntityResolver());
-        assertEquals(2, ld.size());
-
-        MockEnumHolder o1d = (MockEnumHolder) ld.get(0);
-        MockEnumHolder o2d = (MockEnumHolder) ld.get(1);
-        assertSame(MockEnum.b, o1d.getMockEnum());
-        assertSame(MockEnum.c, o2d.getMockEnum());
-    }
-
-    @Test
-    public void testSerializability() throws Exception {
-        MockEnum before = MockEnum.c;
-        Object object = Util.cloneViaSerialization(before);
-        assertNotNull(object);
-        assertSame(before, object);
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/cay_2641/Cay2641IT.java b/cayenne-client/src/test/java/org/apache/cayenne/cay_2641/Cay2641IT.java
deleted file mode 100644
index 3b2d14827..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/cay_2641/Cay2641IT.java
+++ /dev/null
@@ -1,97 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.cay_2641;
-
-import org.apache.cayenne.CayenneContext;
-import org.apache.cayenne.Fault;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.query.ObjectSelect;
-import org.apache.cayenne.testdo.cay_2641.client.ArtistLazy;
-import org.apache.cayenne.testdo.cay_2641.client.PaintingLazy;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.*;
-
-/**
- * @since 4.2
- */
-@UseServerRuntime(CayenneProjects.CAY_2641)
-public class Cay2641IT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Before
-    public void setup() {
-        ArtistLazy artistLazy = context.newObject(ArtistLazy.class);
-        artistLazy.setName("Test");
-        artistLazy.setSurname("Test1");
-
-        PaintingLazy paintingLazy = context.newObject(PaintingLazy.class);
-        paintingLazy.setName("Test");
-        paintingLazy.setArtist(artistLazy);
-
-        context.commitChanges();
-    }
-
-    @Test
-    public void testSampleSelect() {
-        List<ArtistLazy> artists = ObjectSelect.query(ArtistLazy.class).select(context);
-
-        assertEquals(artists.size(), 1);
-        assertEquals(artists.get(0).getSurname(), "Test1");
-
-        assertTrue(artists.get(0).readPropertyDirectly("name") instanceof Fault);
-
-        assertEquals(artists.get(0).getName(), "Test");
-    }
-
-    @Test
-    public void testColumnSelect() {
-        List<String> strings = ObjectSelect.columnQuery(ArtistLazy.class, ArtistLazy.NAME).select(context);
-
-        assertEquals(strings.size(), 1);
-        assertEquals(strings.get(0), "Test");
-    }
-
-    @Test
-    public void testPrefetchSelect() {
-        List<PaintingLazy> paintingLazyList1 = ObjectSelect.query(PaintingLazy.class).prefetch(PaintingLazy.ARTIST.joint()).select(context);
-
-        assertEquals(paintingLazyList1.size(), 1);
-        assertTrue(paintingLazyList1.get(0).getArtist().readPropertyDirectly("name") instanceof Fault);
-
-        List<PaintingLazy> paintingLazyList2 = ObjectSelect.query(PaintingLazy.class).prefetch(PaintingLazy.ARTIST.disjoint()).select(context);
-
-        assertEquals(paintingLazyList2.size(), 1);
-        assertTrue(paintingLazyList1.get(0).getArtist().readPropertyDirectly("name") instanceof Fault);
-
-        List<PaintingLazy> paintingLazyList3 = ObjectSelect.query(PaintingLazy.class).prefetch(PaintingLazy.ARTIST.disjointById()).select(context);
-
-        assertEquals(paintingLazyList3.size(), 1);
-        assertTrue(paintingLazyList1.get(0).getArtist().readPropertyDirectly("name") instanceof Fault);
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientLocalRuntimeTest.java b/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientLocalRuntimeTest.java
deleted file mode 100644
index 46f26286b..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientLocalRuntimeTest.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.ObjectContext;
-import org.apache.cayenne.access.ClientServerChannel;
-import org.apache.cayenne.access.DataContext;
-import org.apache.cayenne.configuration.ObjectContextFactory;
-import org.apache.cayenne.di.DIBootstrap;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.service.LocalConnection;
-import org.junit.Test;
-
-import java.util.Collection;
-
-import static org.junit.Assert.*;
-import static org.mockito.Mockito.mock;
-
-public class ClientLocalRuntimeTest {
-
-    @Test
-	public void testDefaultConstructor() {
-
-		Module serverModule = binder -> {
-        };
-
-		ClientRuntime runtime = ClientRuntime.builder()
-				.disableModulesAutoLoading()
-				.local(DIBootstrap.createInjector(serverModule))
-				.build();
-		Collection<Module> cmodules = runtime.getModules();
-		assertEquals(2, cmodules.size());
-
-		assertTrue(cmodules.toArray()[0] instanceof ClientModule);
-	}
-
-    @Test
-	public void testGetConnection() {
-
-		final DataContext serverContext = mock(DataContext.class);
-
-		Module serverModule = binder -> binder.bind(ObjectContextFactory.class).toInstance(new ObjectContextFactory() {
-
-            public ObjectContext createContext(DataChannel parent) {
-                return null;
-            }
-
-            public ObjectContext createContext() {
-                return serverContext;
-            }
-        });
-
-		ClientRuntime runtime = ClientRuntime.builder()
-				.local(DIBootstrap.createInjector(serverModule))
-				.build();
-
-		ClientConnection connection = runtime.getConnection();
-		assertNotNull(connection);
-		assertTrue(connection instanceof LocalConnection);
-
-		LocalConnection localConnection = (LocalConnection) connection;
-		assertTrue(localConnection.getChannel() instanceof ClientServerChannel);
-		ClientServerChannel clientServerChannel = (ClientServerChannel) localConnection.getChannel();
-		assertSame(serverContext, clientServerChannel.getParentChannel());
-	}
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientModuleTest.java b/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientModuleTest.java
deleted file mode 100644
index 85dfcec14..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientModuleTest.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.configuration.Constants;
-import org.apache.cayenne.configuration.ObjectContextFactory;
-import org.apache.cayenne.configuration.server.ServerModule;
-import org.apache.cayenne.di.Binder;
-import org.apache.cayenne.di.DIBootstrap;
-import org.apache.cayenne.di.Injector;
-import org.apache.cayenne.event.DefaultEventManager;
-import org.apache.cayenne.remote.ClientChannel;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.MockClientConnection;
-import org.junit.Test;
-
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-
-@SuppressWarnings("deprecation")
-public class ClientModuleTest {
-
-    @Test
-    public void testObjectContextFactory() {
-
-        Map<String, String> properties = new HashMap<>();
-        ClientModule module = new ClientModule() {
-
-            @Override
-            public void configure(Binder binder) {
-                super.configure(binder);
-
-                // use a noop connection to prevent startup errors...
-                binder.bind(ClientConnection.class).to(MockClientConnection.class);
-            }
-        };
-
-        Injector injector = DIBootstrap.createInjector(module);
-
-        ObjectContextFactory factory = injector.getInstance(ObjectContextFactory.class);
-        assertNotNull(factory);
-        assertSame("ObjectContextFactory must be a singleton", factory, injector
-                .getInstance(ObjectContextFactory.class));
-    }
-
-    @Test
-    public void testDataChannel() {
-
-        Map<String, String> properties = new HashMap<>();
-        ClientModule module = new ClientModule() {
-
-            @Override
-            public void configure(Binder binder) {
-                super.configure(binder);
-
-                // use a noop connection to prevent startup errors...
-                binder.bind(ClientConnection.class).to(MockClientConnection.class);
-                ServerModule.contributeProperties(binder)
-                        .put(Constants.SERVER_CONTEXTS_SYNC_PROPERTY, String.valueOf(true));
-            }
-        };
-
-        Injector injector = DIBootstrap.createInjector(module);
-
-        DataChannel channel = injector.getInstance(DataChannel.class);
-        assertNotNull(channel);
-        assertTrue(channel instanceof ClientChannel);
-        assertSame("DataChannel must be a singleton", channel, injector
-                .getInstance(DataChannel.class));
-
-        ClientChannel clientChannel = (ClientChannel) channel;
-        assertTrue(clientChannel.getConnection() instanceof MockClientConnection);
-        assertTrue(clientChannel.getEventManager() instanceof DefaultEventManager);
-        assertFalse(clientChannel.isChannelEventsEnabled());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeBuilderTest.java b/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeBuilderTest.java
deleted file mode 100644
index eb9fe3208..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeBuilderTest.java
+++ /dev/null
@@ -1,160 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.Map;
-
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.configuration.Constants;
-import org.apache.cayenne.configuration.server.ServerModule;
-import org.apache.cayenne.di.DIBootstrap;
-import org.apache.cayenne.di.Injector;
-import org.apache.cayenne.di.Key;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.di.Binder;
-import org.apache.cayenne.remote.ClientChannel;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.MockClientConnection;
-import org.apache.cayenne.rop.HttpClientConnection;
-import org.junit.After;
-import org.junit.Test;
-
-import static org.hamcrest.CoreMatchers.instanceOf;
-import static org.junit.Assert.*;
-import static org.mockito.Mockito.mock;
-
-/**
- * @since 4.0
- */
-public class ClientRuntimeBuilderTest {
-
-    private ClientRuntime runtime;
-
-    @After
-    public void stopRuntime() {
-        if (runtime != null) {
-            runtime.shutdown();
-        }
-    }
-
-    @Test
-    public void testDefaultBuild() {
-        runtime = new ClientRuntimeBuilder().build();
-
-        Map<String, String> properties = runtime.getInjector()
-                .getInstance(Key.getMapOf(String.class, String.class, Constants.PROPERTIES_MAP));
-        assertTrue(properties.isEmpty());
-
-        Collection<Module> modules = runtime.getModules();
-        assertEquals(1, modules.size());
-        assertThat(modules.iterator().next(), instanceOf(ClientModule.class));
-    }
-
-    @Test
-    public void testNoAutoLoading() {
-        runtime = new ClientRuntimeBuilder().disableModulesAutoLoading().build();
-
-        Map<String, String> properties = runtime.getInjector()
-                .getInstance(Key.getMapOf(String.class, String.class, Constants.PROPERTIES_MAP));
-        assertTrue(properties.isEmpty());
-
-        Collection<Module> modules = runtime.getModules();
-        assertEquals(1, modules.size());
-        assertThat(modules.iterator().next(), instanceOf(ClientModule.class));
-    }
-
-    @Test
-    public void testExtraModules() {
-
-        Module m = mock(Module.class);
-
-        runtime = new ClientRuntimeBuilder().addModule(m).build();
-
-        Collection<Module> modules = runtime.getModules();
-        assertEquals(2, modules.size());
-        Module[] array = modules.toArray(new Module[2]);
-        assertThat(array[0], instanceOf(ClientModule.class));
-        assertSame(m, array[1]);
-    }
-
-    @Test
-    public void testProperties() {
-        Map<String, String> properties = Collections.singletonMap("test", "test_value");
-
-        runtime = new ClientRuntimeBuilder().properties(properties).build();
-
-        Map<String, String> injectedProperties = runtime.getInjector()
-                .getInstance(Key.getMapOf(String.class, String.class, Constants.PROPERTIES_MAP));
-        assertEquals(properties, injectedProperties);
-    }
-
-    @Test
-    public void testClientConnection() {
-
-        Map<String, String> properties1 = new HashMap<>();
-        properties1.put(ClientConstants.ROP_SERVICE_URL_PROPERTY, "http://localhost/YuM");
-        ClientModule module = new ClientModule(){
-
-            @Override
-            public void configure(Binder binder) {
-                super.configure(binder);
-                ServerModule.contributeProperties(binder).putAll(properties1);
-            }
-        };
-
-
-        Injector injector = DIBootstrap.createInjector(module);
-
-        ClientConnection connection = injector.getInstance(ClientConnection.class);
-        assertNotNull(connection);
-        assertTrue(connection instanceof HttpClientConnection);
-
-        assertSame("Connection must be a singleton", connection, injector
-                .getInstance(ClientConnection.class));
-    }
-
-    @Test
-    public void testDataChannel_NoChannelEvents() {
-
-        Map<String, String> properties1 = new HashMap<>();
-        properties1.put(ClientConstants.ROP_CHANNEL_EVENTS_PROPERTY, "true");
-        ClientModule module = new ClientModule() {
-
-            @Override
-            public void configure(Binder binder) {
-                super.configure(binder);
-
-                // use a noop connection to prevent startup errors...
-                binder.bind(ClientConnection.class).to(MockClientConnection.class);
-
-                ServerModule.contributeProperties(binder).putAll(properties1);
-            }
-        };
-
-        Injector injector = DIBootstrap.createInjector(module);
-
-        DataChannel channel = injector.getInstance(DataChannel.class);
-        ClientChannel clientChannel = (ClientChannel) channel;
-        assertTrue(clientChannel.isChannelEventsEnabled());
-    }
-}
\ No newline at end of file
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeTest.java b/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeTest.java
deleted file mode 100644
index 736671a16..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/ClientRuntimeTest.java
+++ /dev/null
@@ -1,118 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.configuration.rop.client;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import org.apache.cayenne.CayenneContext;
-import org.apache.cayenne.DataChannel;
-import org.apache.cayenne.ObjectContext;
-import org.apache.cayenne.configuration.Constants;
-import org.apache.cayenne.configuration.server.ServerModule;
-import org.apache.cayenne.di.Binder;
-import org.apache.cayenne.di.Module;
-import org.apache.cayenne.event.DefaultEventManager;
-import org.apache.cayenne.event.EventManager;
-import org.apache.cayenne.remote.ClientChannel;
-import org.apache.cayenne.remote.ClientConnection;
-import org.apache.cayenne.remote.MockClientConnection;
-import org.junit.Test;
-
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNotSame;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-
-@SuppressWarnings("deprecation")
-public class ClientRuntimeTest {
-
-    @Test
-	public void testGetObjectContext() {
-
-		Map<String, String> properties = new HashMap<>();
-		ClientModule extraModule = new ClientModule() {
-
-			@Override
-			public void configure(Binder binder) {
-				super.configure(binder);
-
-				// use a noop connection to prevent startup errors...
-				binder.bind(ClientConnection.class).to(MockClientConnection.class);
-			}
-		};
-
-		ClientRuntime runtime = ClientRuntime.builder()
-								.properties(properties)
-								.addModule(extraModule)
-								.build();
-
-		ObjectContext context = runtime.newContext();
-		assertNotNull(context);
-		assertTrue(context instanceof CayenneContext);
-		assertNotSame("ObjectContext must not be a singleton", context, runtime.newContext());
-
-		CayenneContext clientContext = (CayenneContext) context;
-		assertNotNull(clientContext.getChannel());
-		assertSame(runtime.getChannel(), clientContext.getChannel());
-	}
-
-    @Test
-	public void testGetDataChannel() {
-
-		Map<String, String> properties = new HashMap<>();
-
-		Module extraModule = binder ->
-            // use a noop connection to prevent hessian startup errors...
-            binder.bind(ClientConnection.class).to(MockClientConnection.class);
-
-
-		ClientRuntime runtime = ClientRuntime.builder()
-								.properties(properties)
-								.addModule(extraModule)
-								.build();
-
-		DataChannel channel = runtime.getChannel();
-		assertNotNull(channel);
-		assertTrue(channel instanceof ClientChannel);
-	}
-
-    @Test
-	public void testShutdown() throws Exception {
-
-		Map<String, String> properties = new HashMap<>();
-		ClientRuntime runtime = ClientRuntime.builder()
-								.properties(properties)
-								.addModule(binder -> ServerModule.contributeProperties(binder)
-										.put(Constants.SERVER_CONTEXTS_SYNC_PROPERTY, String.valueOf(true)))
-								.build();
-
-		// make sure objects to be shut down are resolved
-
-		EventManager em = runtime.getInjector().getInstance(EventManager.class);
-		assertNotNull(em);
-		assertTrue(em instanceof DefaultEventManager);
-		assertFalse(((DefaultEventManager) em).isStopped());
-
-		runtime.getInjector().shutdown();
-
-		assertTrue(((DefaultEventManager) em).isStopped());
-	}
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/MainCayenneClientModuleProviderTest.java b/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/MainCayenneClientModuleProviderTest.java
deleted file mode 100644
index a17688b6f..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/configuration/rop/client/MainCayenneClientModuleProviderTest.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.configuration.rop.client;
-
-import org.apache.cayenne.unit.util.ModuleProviderChecker;
-import org.junit.Test;
-
-/**
- * @since 4.0
- */
-public class MainCayenneClientModuleProviderTest {
-
-    @Test
-    public void testAutoLoadable() {
-        ModuleProviderChecker.testProviderPresent(MainCayenneClientModuleProvider.class, CayenneClientModuleProvider.class);
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/event/EventSubjectTest.java b/cayenne-client/src/test/java/org/apache/cayenne/event/EventSubjectTest.java
deleted file mode 100644
index 799f2176d..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/event/EventSubjectTest.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.event;
-
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotSame;
-
-public class EventSubjectTest {
-
-    @Test
-    public void testEqualityOfClonedSubjectsHessian() throws Exception {
-        EventSubject s1 = EventSubject.getSubject(EventSubjectTest.class, "MySubject");
-        EventSubject s2 = (EventSubject) HessianUtil.cloneViaClientServerSerialization(s1, new EntityResolver());
-
-        assertNotSame(s1, s2);
-        assertEquals(s1, s2);
-        assertEquals(s1.hashCode(), s2.hashCode());
-    }
-
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/graph/NodeDiffTest.java b/cayenne-client/src/test/java/org/apache/cayenne/graph/NodeDiffTest.java
deleted file mode 100644
index 70f7109e5..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/graph/NodeDiffTest.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.graph;
-
-import org.apache.cayenne.map.EntityResolver;
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-
-public class NodeDiffTest {
-
-	@Test
-	public void testHessianSerialization() throws Exception {
-
-		// id must be a serializable object...
-		String id = "abcd";
-		NodeDiff diff = new ConcreteNodeDiff(id);
-
-		Object d = HessianUtil.cloneViaClientServerSerialization(diff, new EntityResolver());
-		assertNotNull(d);
-		assertNotNull(((NodeDiff) d).getNodeId());
-		assertEquals(id, ((NodeDiff) d).getNodeId());
-	}
-
-	@SuppressWarnings("serial")
-	static class ConcreteNodeDiff extends NodeDiff {
-
-		ConcreteNodeDiff(Object id) {
-			super(id);
-		}
-
-		@Override
-		public void apply(GraphChangeHandler tracker) {
-		}
-
-		@Override
-		public void undo(GraphChangeHandler tracker) {
-		}
-	}
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/map/ClientEntityResolverTest.java b/cayenne-client/src/test/java/org/apache/cayenne/map/ClientEntityResolverTest.java
deleted file mode 100644
index a6ac129d9..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/map/ClientEntityResolverTest.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.map;
-
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.apache.cayenne.testdo.testmap.Artist;
-import org.junit.Test;
-
-import java.util.Collection;
-import java.util.Collections;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNotSame;
-import static org.junit.Assert.assertTrue;
-
-public class ClientEntityResolverTest {
-
-    @Test
-    public void testSerializabilityWithHessian() throws Exception {
-        ObjEntity entity = new ObjEntity("test_entity");
-        entity.setClassName(Artist.class.getName());
-
-        DataMap dataMap = new DataMap("test");
-        dataMap.addObjEntity(entity);
-        Collection<DataMap> maps = Collections.singleton(dataMap);
-        EntityResolver resolver = new EntityResolver(maps);
-
-        // 1. simple case
-        Object c1 = HessianUtil.cloneViaClientServerSerialization(resolver, new EntityResolver());
-
-        assertNotNull(c1);
-        assertTrue(c1 instanceof EntityResolver);
-        EntityResolver cr1 = (EntityResolver) c1;
-
-        assertNotSame(resolver, cr1);
-        assertEquals(1, cr1.getObjEntities().size());
-        assertNotNull(cr1.getObjEntity(entity.getName()));
-
-        // 2. with descriptors resolved...
-        assertNotNull(resolver.getClassDescriptor(entity.getName()));
-
-        EntityResolver cr2 = (EntityResolver) HessianUtil.cloneViaClientServerSerialization(resolver,
-                new EntityResolver());
-        assertNotNull(cr2);
-        assertEquals(1, cr2.getObjEntities().size());
-        assertNotNull(cr2.getObjEntity(entity.getName()));
-        assertNotNull(cr2.getClassDescriptor(entity.getName()));
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/map/ClientObjectRelationshipTest.java b/cayenne-client/src/test/java/org/apache/cayenne/map/ClientObjectRelationshipTest.java
deleted file mode 100644
index 00dc6227d..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/map/ClientObjectRelationshipTest.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.map;
-
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNull;
-
-public class ClientObjectRelationshipTest {
-
-    @Test
-    public void testSerializabilityViaHessian() throws Exception {
-
-        ClientObjRelationship r1 = new ClientObjRelationship("r1", "rr1", true, true);
-        ClientObjRelationship r2 = (ClientObjRelationship) HessianUtil.cloneViaClientServerSerialization(r1,
-                new EntityResolver());
-        assertEquals(r1.getName(), r2.getName());
-        assertEquals(r1.getReverseRelationship(), r2.getReverseRelationship());
-        assertEquals(r1.isToMany(), r2.isToMany());
-        assertEquals(r1.isReadOnly(), r2.isReadOnly());
-
-        ClientObjRelationship r3 = new ClientObjRelationship("r3", null, false, false);
-        ClientObjRelationship r4 = (ClientObjRelationship) HessianUtil.cloneViaClientServerSerialization(r3,
-                new EntityResolver());
-        assertEquals(r3.getName(), r4.getName());
-        assertNull(r4.getReverseRelationship());
-        assertEquals(r3.isToMany(), r4.isToMany());
-        assertEquals(r3.isReadOnly(), r4.isReadOnly());
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/map/DataMapTest.java b/cayenne-client/src/test/java/org/apache/cayenne/map/DataMapTest.java
deleted file mode 100644
index b59a850f8..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/map/DataMapTest.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.map;
-
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.apache.cayenne.util.Util;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-
-public class DataMapTest {
-
-    @Test
-    public void testSerializabilityWithHessian() throws Exception {
-        DataMap m1 = new DataMap("abc");
-        DataMap d1 = (DataMap) HessianUtil.cloneViaClientServerSerialization(m1, new EntityResolver());
-        assertEquals(m1.getName(), d1.getName());
-
-        ObjEntity oe1 = new ObjEntity("oe1");
-        m1.addObjEntity(oe1);
-
-        DataMap d2 = (DataMap) Util.cloneViaSerialization(m1);
-        assertNotNull(d2.getObjEntity(oe1.getName()));
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/map/DbEntityTest.java b/cayenne-client/src/test/java/org/apache/cayenne/map/DbEntityTest.java
deleted file mode 100644
index 16a2d0873..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/map/DbEntityTest.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.map;
-
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-
-public class DbEntityTest {
-
-    @Test
-    public void testSerializabilityWithHessian() throws Exception {
-        DbEntity entity = new DbEntity("entity");
-
-        DbAttribute pk = new DbAttribute("pk");
-        pk.setPrimaryKey(true);
-        entity.addAttribute(pk);
-
-        DbAttribute generated = new DbAttribute("generated");
-        generated.setGenerated(true);
-        entity.addAttribute(generated);
-
-        DbEntity d2 = (DbEntity) HessianUtil.cloneViaClientServerSerialization(entity, new EntityResolver());
-
-        assertNotNull(d2.getPrimaryKeys());
-        assertEquals(entity.getPrimaryKeys().size(), d2.getPrimaryKeys().size());
-
-        DbAttribute pk2 = d2.getAttribute(pk.getName());
-        assertNotNull(pk2);
-        assertTrue(d2.getPrimaryKeys().contains(pk2));
-
-        assertNotNull(d2.getGeneratedAttributes());
-        assertEquals(entity.getGeneratedAttributes().size(), d2.getGeneratedAttributes().size());
-
-        DbAttribute generated2 = d2.getAttribute(generated.getName());
-        assertNotNull(generated2);
-        assertTrue(d2.getGeneratedAttributes().contains(generated2));
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/map/EntityTest.java b/cayenne-client/src/test/java/org/apache/cayenne/map/EntityTest.java
deleted file mode 100644
index ef6a302b7..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/map/EntityTest.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.map;
-
-import org.apache.cayenne.remote.hessian.service.HessianUtil;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertSame;
-import static org.junit.Assert.assertTrue;
-
-public class EntityTest {
-
-    @Test
-    public void testSerializabilityWithHessian() throws Exception {
-        Entity entity = new MockEntity("entity");
-
-        Entity d1 = (Entity) HessianUtil.cloneViaClientServerSerialization(
-                entity,
-                new EntityResolver());
-        assertEquals(entity.getName(), d1.getName());
-
-        entity.addAttribute(new MockAttribute("abc"));
-        entity.addRelationship(new MockRelationship("xyz"));
-        Entity d2 = (Entity) HessianUtil.cloneViaClientServerSerialization(
-                entity,
-                new EntityResolver());
-        assertNotNull(d2.getAttribute("abc"));
-        assertNotNull(d2.getRelationship("xyz"));
-
-        // test that ref collection wrappers are still working
-        assertNotNull(d2.getAttributes());
-        assertEquals(entity.getAttributes().size(), d2.getAttributes().size());
-        assertTrue(d2.getAttributes().contains(d2.getAttribute("abc")));
-
-        assertNotNull(d2.getRelationships());
-        assertEquals(entity.getRelationships().size(), d2.getRelationships().size());
-        assertTrue(d2.getAttributes().contains(d2.getAttribute("abc")));
-
-        assertNotNull(d2.getAttributeMap());
-        assertEquals(entity.getAttributes().size(), d2.getAttributeMap().size());
-        assertSame(d2.getAttribute("abc"), d2.getAttributeMap().get("abc"));
-
-        assertNotNull(d2.getRelationshipMap());
-        assertEquals(entity.getRelationships().size(), d2.getRelationshipMap().size());
-        assertSame(d2.getRelationship("xyz"), d2.getRelationshipMap().get("xyz"));
-    }
-}
diff --git a/cayenne-client/src/test/java/org/apache/cayenne/query/ClientExpressionIT.java b/cayenne-client/src/test/java/org/apache/cayenne/query/ClientExpressionIT.java
deleted file mode 100644
index 9681b2aa7..000000000
--- a/cayenne-client/src/test/java/org/apache/cayenne/query/ClientExpressionIT.java
+++ /dev/null
@@ -1,346 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    https://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.query;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import org.apache.cayenne.CayenneContext;
-import org.apache.cayenne.ObjectId;
-import org.apache.cayenne.di.Inject;
-import org.apache.cayenne.exp.Expression;
-import org.apache.cayenne.exp.ExpressionFactory;
-import org.apache.cayenne.exp.parser.ASTEqual;
-import org.apache.cayenne.exp.parser.ASTList;
-import org.apache.cayenne.test.jdbc.DBHelper;
-import org.apache.cayenne.test.jdbc.TableHelper;
-import org.apache.cayenne.testdo.mt.ClientMtTable1;
-import org.apache.cayenne.testdo.mt.ClientMtTable2;
-import org.apache.cayenne.unit.di.client.ClientCase;
-import org.apache.cayenne.unit.di.server.CayenneProjects;
-import org.apache.cayenne.unit.di.server.UseServerRuntime;
-import org.junit.Before;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNotSame;
-
-@UseServerRuntime(CayenneProjects.MULTI_TIER_PROJECT)
-public class ClientExpressionIT extends ClientCase {
-
-    @Inject
-    private CayenneContext context;
-
-    @Inject
-    private DBHelper dbHelper;
-
-    private TableHelper tMtTable1;
-    private TableHelper tMtTable2;
-
-    @Before
-    public void setUp() throws Exception {
-        tMtTable1 = new TableHelper(dbHelper, "MT_TABLE1");
-        tMtTable1.setColumns("TABLE1_ID", "GLOBAL_ATTRIBUTE1", "SERVER_ATTRIBUTE1");
-
-        tMtTable2 = new TableHelper(dbHelper, "MT_TABLE2");
-        tMtTable2.setColumns("TABLE2_ID", "TABLE1_ID", "GLOBAL_ATTRIBUTE");
-    }
-
-    private void createDataSet() throws Exception {
-        for(int i = 1; i <= 10; i++) {
-            tMtTable1.insert(i ,"1_global" + i, "server" + i);
-            tMtTable2.insert(i , i, "2_global" + i);
-            tMtTable2.insert(i + 10, i, "2_global" + (i + 10));
-        }
-    }
-
-    @Test
-    public void testPersistentValueInExpression() {
-        ClientMtTable1 t1 = context.newObject(ClientMtTable1.class);
-        ClientMtTable1 t2 = context.newObject(ClientMtTable1.class);
-
-        context.commitChanges();
-
-        Expression scalar = ExpressionFactory.matchExp((String)null, t1);
-        Expression list = ExpressionFactory.matchAllExp("|", Arrays.asList(t1, t2));
-
-        assertEquals(t1.getObjectId(), scalar.getOperand(1));
-        assertEquals(t1.getObjectId(), ((ASTEqual)list.getOperand(0)).getOperand(1));
-        assertEquals(t2.getObjectId(), ((ASTEqual)list.getOperand(1)).getOperand(1));
-    }
-
-    @Test
-    public void testListInASTList() {
-        ClientMtTable1 t1 = context.newObject(ClientMtTable1.class);
-        ClientMtTable1 t2 = context.newObject(ClientMtTable1.class);
-
-        context.commitChanges();
-
-        List<ClientMtTable1> table1List = new ArrayList<>();
-        table1List.add(t1);
-        table1List.add(t2);
-
-        // send list in expression factory
-        Expression list = ClientMtTable2.TABLE1.in(table1List);
-
-        Object[] values = (Object[])((ASTList)list.getOperand(1)).getOperand(0);
-        assertEquals(t1.getObjectId(), values[0]);
-        assertEquals(t2.getObjectId(), values[1]);
-
-        ObjectId t1Id = ObjectId.of("MtTable1", "TABLE1_ID", 1);
-        ObjectId t2Id = ObjectId.of("MtTable1", "TABLE1_ID", 2);
-        t1.setObjectId(t1Id);
-        t2.setObjectId(t2Id);
-
-        //Expression and client have different copies of object
-        assertNotSame(t1.getObjectId(), values[0]);
-        assertNotSame(t2.getObjectId(), values[1]);
-    }
-
-    @Test
-    public void testArrayInASTList() {
-        ClientMtTable1 t1 = context.newObject(ClientMtTable1.class);
-        ClientMtTable1 t2 = context.newObject(ClientMtTable1.class);
-        ClientMtTable1 t3 = context.newObject(ClientMtTable1.class);
-
-        context.commitChanges();
-
-        Object[] tArray = new Object[3];
-        tArray[0] = t1;
-        tArray[1] = t2;
-
-        // send array in expression factory
-        Expression list = ExpressionFactory.inExp(ClientMtTable2.TABLE1.getName(), tArray);
-        tArray[2] = t3;
-
-        Object[] values = (Object[])((ASTList)list.getOperand(1)).getOperand(0);
-        assertEquals(tArray.length, values.length);
-        assertNotSame(tArray[2], values[2]);
-        assertEquals(t1.getObjectId(), values[0]);
-        assertEquals(t2.getObjectId(), values[1]);
-
-        ObjectId t1Id = ObjectId.of("MtTable1", "TABLE1_ID", 1);
-        ObjectId t2Id = ObjectId.of("MtTable1", "TABLE1_ID", 2);
-        t1.setObjectId(t1Id);
-        t2.setObjectId(t2Id);
-
-        // Expression and client have different arrays
-        assertNotSame(t1.getObjectId(), values[0]);
-        assertNotSame(t2.getObjectId(), values[1]);
-    }
-
-    @Test
-    public void testExpressionFactoryMatch() throws Exception {
-        createDataSet();
-
-        ObjectSelect<ClientMtTable1> table1Query = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(new Ordering("db:TABLE1_ID", SortOrder.ASCENDING));
-        List<ClientMtTable1> table1List = table1Query.select(context);
-
-        assertNotNull(table1List);
-
-        ClientMtTable1 element_1 = table1List.get(0);
-        ClientMtTable1 element_2 = table1List.get(1);
-
-        Expression exp = ClientMtTable2.TABLE1.eq(element_1);
-        ObjectSelect<ClientMtTable2> table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .where(exp);
-        List<ClientMtTable2> table2List = table2Query.select(context);
-
-        assertNotNull(table2List);
-        assertEquals(2, table2List.size());
-
-        exp = ExpressionFactory.matchExp(element_2);
-        table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .where(exp);
-        table2List = context.select(table2Query);
-
-        assertNotNull(table2List);
-        assertEquals(2, table2List.size());
-    }
-
-    @Test
-    public void testExpressionFactoryMatchAll() throws Exception {
-        createDataSet();
-
-        ObjectSelect<ClientMtTable2> table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .orderBy(new Ordering("db:TABLE2_ID", SortOrder.ASCENDING));
-        List<ClientMtTable2> table2List = context.select(table2Query);
-
-        ClientMtTable2 element_1 = table2List.get(0);
-        ClientMtTable2 element_2 = table2List.get(10);
-
-        assertEquals(element_1.getTable1(), element_2.getTable1());
-
-        Expression exp = ExpressionFactory.matchAllExp("|" + ClientMtTable1.TABLE2ARRAY.getName(), Arrays.asList(element_1, element_2));
-        ObjectSelect<ClientMtTable1> table1Query = ObjectSelect.query(ClientMtTable1.class)
-                .where(exp);
-        List<ClientMtTable1> table1List = table1Query.select(context);
-
-        assertEquals(1, table1List.size());
-    }
-
-    @Test
-    public void testExpressionFactoryMatchAny() throws Exception {
-        createDataSet();
-
-        ObjectSelect<ClientMtTable2> table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .orderBy(new Ordering("db:TABLE2_ID", SortOrder.ASCENDING));
-        List<ClientMtTable2> table2List = context.select(table2Query);
-
-        ClientMtTable2 element_1 = table2List.get(0);
-        ClientMtTable2 element_2 = table2List.get(10);
-
-        Expression exp = ExpressionFactory.matchAnyExp(element_1, element_2);
-        table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .where(exp);
-        table2List = context.select(table2Query);
-
-        assertEquals(2, table2List.size());
-    }
-
-    @Test
-    public void testExpressionFactoryIn() throws Exception {
-        createDataSet();
-
-        ObjectSelect<ClientMtTable1> table1Query = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(new Ordering("db:TABLE1_ID", SortOrder.ASCENDING));
-        List<ClientMtTable1> table1List = context.select(table1Query);
-
-        ClientMtTable1 element_3 = table1List.get(2);
-        ClientMtTable1 element_8 = table1List.get(7);
-
-        // IN expression via Collection
-        Expression exp = ExpressionFactory.inExp(ClientMtTable2.TABLE1.getName(), table1List.subList(3, 6));
-        ObjectSelect<ClientMtTable2> table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .where(exp);
-        List<ClientMtTable2> table2List = context.select(table2Query);
-
-        assertEquals(6, table2List.size());
-
-        // IN expression via Array
-        exp = ExpressionFactory.inExp(ClientMtTable2.TABLE1.getName(), element_3, element_8);
-        table2Query = ObjectSelect.query(ClientMtTable2.class)
-                .where(exp);
-        table2List = context.select(table2Query);
-
-        assertEquals(4, table2List.size());
-    }
-
-    @Test
-    public void testExpressionFactoryBetween() throws Exception {
-        createDataSet();
-
-        ObjectSelect<ClientMtTable1> table1Query = ObjectSelect.query(ClientMtTable1.class)
-                .orderBy(new Ordering("db:TABLE1_ID", SortOrder.ASCENDING));
... 13052 lines suppressed ...