Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSimon McDuff2008-06-13 20:33:50 +0000
committerSimon McDuff2008-06-13 20:33:50 +0000
commit9bbbde7205f79ad16a06322bbb64f5b7025dd4a8 (patch)
tree53495acdc5392899a2f191be6a3c3510a002c78a
parentbdbfa6d5b823d53f661b86998bdb1ff5772b7e4d (diff)
downloadcdo-9bbbde7205f79ad16a06322bbb64f5b7025dd4a8.tar.gz
cdo-9bbbde7205f79ad16a06322bbb64f5b7025dd4a8.tar.xz
cdo-9bbbde7205f79ad16a06322bbb64f5b7025dd4a8.zip
[233490] Change Subscription
https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
-rw-r--r--plugins/org.eclipse.emf.cdo.common/src/org/eclipse/emf/cdo/common/CDOProtocolConstants.java6
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/NotificationManager.java56
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Repository.java14
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Session.java32
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/SessionManager.java5
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Transaction.java14
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/View.java27
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/CDOServerProtocol.java7
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/ChangeSubscriptionIndication.java81
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/InvalidationNotification.java22
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/OpenSessionIndication.java13
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/PassiveUpdateIndication.java2
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/INotificationManager.java24
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IRepository.java3
-rw-r--r--plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IView.java4
-rw-r--r--plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/AllTests.java2
-rw-r--r--plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/ChangeSubscriptionTest.java575
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOChangeSubscriptionPolicy.java38
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDONotification.java26
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOView.java6
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationBuilder.java130
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationImpl.java212
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOObjectImpl.java42
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOSessionImpl.java42
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOTransactionImpl.java10
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOViewImpl.java229
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/ChangeSubscriptionRequest.java76
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/InvalidationIndication.java22
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/OpenSessionRequest.java14
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/PassiveUpdateRequest.java2
-rw-r--r--plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/SyncRevisionRequest.java2
31 files changed, 1699 insertions, 39 deletions
diff --git a/plugins/org.eclipse.emf.cdo.common/src/org/eclipse/emf/cdo/common/CDOProtocolConstants.java b/plugins/org.eclipse.emf.cdo.common/src/org/eclipse/emf/cdo/common/CDOProtocolConstants.java
index 39a2be0089..54f4556a24 100644
--- a/plugins/org.eclipse.emf.cdo.common/src/org/eclipse/emf/cdo/common/CDOProtocolConstants.java
+++ b/plugins/org.eclipse.emf.cdo.common/src/org/eclipse/emf/cdo/common/CDOProtocolConstants.java
@@ -9,6 +9,8 @@
* Eike Stepper - initial API and implementation
* Simon McDuff - 230832: Make remote invalidation configurable
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.common;
@@ -53,7 +55,9 @@ public interface CDOProtocolConstants
public static final short SIGNAL_SYNC = 17;
- public static final short SIGNAL_AUTOMATIC_REFRESH = 18;
+ public static final short SIGNAL_PASSIVE_UPDATE = 18;
+
+ public static final short SIGNAL_CHANGE_SUBSCRIPTION = 19;
public static final int ERROR_REPOSITORY_NOT_FOUND = -1;
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/NotificationManager.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/NotificationManager.java
new file mode 100644
index 0000000000..b06e9e73bb
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/NotificationManager.java
@@ -0,0 +1,56 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.cdo.internal.server;
+
+import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
+import org.eclipse.emf.cdo.server.INotificationManager;
+import org.eclipse.emf.cdo.server.IStoreWriter.CommitContext;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author Simon McDuff
+ */
+public class NotificationManager implements INotificationManager
+{
+ private Repository repository = null;
+
+ public NotificationManager(Repository repository)
+ {
+ this.repository = repository;
+ }
+
+ public void notifyInvalidation(Session session, CommitContext commitContext)
+ {
+ CDORevisionDelta[] dirtyObjectDeltas = commitContext.getDirtyObjectDeltas();
+
+ int modifications = dirtyObjectDeltas.length;
+
+ if (modifications > 0)
+ {
+ List<CDOID> dirtyIDs = new ArrayList<CDOID>(modifications);
+ List<CDORevisionDelta> deltas = new ArrayList<CDORevisionDelta>(modifications);
+
+ for (int i = 0; i < modifications; i++)
+ {
+ dirtyIDs.add(dirtyObjectDeltas[i].getID());
+ deltas.add(dirtyObjectDeltas[i]);
+ }
+
+ SessionManager sessionManager = (SessionManager)repository.getSessionManager();
+
+ sessionManager.notifyInvalidation(commitContext.getTimeStamp(), dirtyIDs, deltas, session);
+ }
+
+ }
+}
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Repository.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Repository.java
index 2d3c706638..885b8f7214 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Repository.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Repository.java
@@ -10,7 +10,8 @@
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=201266
* Simon McDuff - 233273: [QUERY] Develop Query mechanism
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=233273
- *
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.internal.server;
@@ -58,6 +59,8 @@ public class Repository extends Container<IRepositoryElement> implements IReposi
private RevisionManager revisionManager = createRevisionManager();
private QueryManager queryManager = createQueryManager();
+
+ private NotificationManager notificationManager = createNotificationManager();
private IRepositoryElement[] elements;
@@ -172,6 +175,11 @@ public class Repository extends Container<IRepositoryElement> implements IReposi
return queryManager;
}
+ public NotificationManager getNotificationManager()
+ {
+ return notificationManager;
+ }
+
public IRepositoryElement[] getElements()
{
return elements;
@@ -230,6 +238,10 @@ public class Repository extends Container<IRepositoryElement> implements IReposi
{
return new QueryManager();
}
+ protected NotificationManager createNotificationManager()
+ {
+ return new NotificationManager(this);
+ }
@Override
protected void doBeforeActivate() throws Exception
{
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Session.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Session.java
index 5d701197d0..a8f816900c 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Session.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Session.java
@@ -10,6 +10,8 @@
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=201266
* Simon McDuff - 230832: Make remote invalidation configurable
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.internal.server;
@@ -21,6 +23,7 @@ import org.eclipse.emf.cdo.common.id.CDOIDProvider;
import org.eclipse.emf.cdo.common.model.CDOClass;
import org.eclipse.emf.cdo.common.model.CDOClassRef;
import org.eclipse.emf.cdo.common.model.CDOFeature;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
import org.eclipse.emf.cdo.internal.server.bundle.OM;
import org.eclipse.emf.cdo.internal.server.protocol.CDOServerProtocol;
import org.eclipse.emf.cdo.internal.server.protocol.InvalidationNotification;
@@ -37,6 +40,7 @@ import org.eclipse.net4j.util.lifecycle.ILifecycle;
import org.eclipse.net4j.util.lifecycle.LifecycleEventAdapter;
import java.text.MessageFormat;
+import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
@@ -52,7 +56,7 @@ public class Session extends Container<IView> implements ISession, CDOIDProvider
private CDOServerProtocol protocol;
private int sessionID;
-
+
private boolean passiveUpdateEnabled = true;
private boolean legacySupportEnabled;
@@ -201,14 +205,28 @@ public class Session extends Container<IView> implements ISession, CDOIDProvider
return new View(this, viewID, type);
}
- public void notifyInvalidation(long timeStamp, List<CDOID> dirtyIDs)
- {
- if (!isPassiveUpdateEnabled())
- return;
-
+ public void notifyInvalidation(long timeStamp, List<CDOID> dirtyIDs, List<CDORevisionDelta> deltas)
+ {
+ if (!isPassiveUpdateEnabled()) dirtyIDs = new ArrayList<CDOID>();
+
+ // Look if someone needs to know something about modified objects
+ List<CDORevisionDelta> newDeltas = new ArrayList<CDORevisionDelta>();
+ for (CDORevisionDelta delta : deltas)
+ {
+ CDOID lookupID = delta.getID();
+ for (IView view : views.values())
+ {
+ if (((View)view).isSubscribe(lookupID))
+ {
+ newDeltas.add(delta);
+ break;
+ }
+ }
+ }
try
{
- new InvalidationNotification(protocol.getChannel(), timeStamp, dirtyIDs).send();
+ if (dirtyIDs.size() > 0 || newDeltas.size() > 0)
+ new InvalidationNotification(protocol.getChannel(), this, timeStamp, dirtyIDs, newDeltas).send();
}
catch (Exception ex)
{
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/SessionManager.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/SessionManager.java
index 02cfb5ad0a..186033a0a8 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/SessionManager.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/SessionManager.java
@@ -13,6 +13,7 @@
package org.eclipse.emf.cdo.internal.server;
import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
import org.eclipse.emf.cdo.internal.server.bundle.OM;
import org.eclipse.emf.cdo.internal.server.protocol.CDOServerProtocol;
import org.eclipse.emf.cdo.server.ISession;
@@ -104,13 +105,13 @@ public class SessionManager extends Container<ISession> implements ISessionManag
}
}
- public void notifyInvalidation(long timeStamp, List<CDOID> dirtyIDs, Session excludedSession)
+ public void notifyInvalidation(long timeStamp, List<CDOID> dirtyIDs, List<CDORevisionDelta> deltas, Session excludedSession)
{
for (Session session : getSessions())
{
if (session != excludedSession)
{
- session.notifyInvalidation(timeStamp, dirtyIDs);
+ session.notifyInvalidation(timeStamp, dirtyIDs, deltas);
}
}
}
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Transaction.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Transaction.java
index 25cc439d40..423f7bbce8 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Transaction.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/Transaction.java
@@ -7,6 +7,8 @@
*
* Contributors:
* Eike Stepper - initial API and implementation
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.internal.server;
@@ -196,17 +198,9 @@ public class Transaction extends View implements ITransaction, IStoreWriter.Comm
{
try
{
- int modifications = dirtyObjectDeltas.length;
- if (success && modifications > 0)
+ if (success)
{
- List<CDOID> dirtyIDs = new ArrayList<CDOID>(modifications);
- for (int i = 0; i < modifications; i++)
- {
- dirtyIDs.add(dirtyObjectDeltas[i].getID());
- }
-
- SessionManager sessionManager = (SessionManager)repository.getSessionManager();
- sessionManager.notifyInvalidation(timeStamp, dirtyIDs, getSession());
+ repository.getNotificationManager().notifyInvalidation( getSession(), this);
}
}
finally
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/View.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/View.java
index eeb793b4e9..e142ce9b1a 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/View.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/View.java
@@ -7,12 +7,17 @@
*
* Contributors:
* Eike Stepper - initial API and implementation
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.internal.server;
+import org.eclipse.emf.cdo.common.id.CDOID;
import org.eclipse.emf.cdo.server.IView;
import java.text.MessageFormat;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
/**
* @author Eike Stepper
@@ -25,6 +30,8 @@ public class View implements IView
private Type viewType;
+ private Map<CDOID, CDOID> changeSubscriptionObjects = new ConcurrentHashMap<CDOID, CDOID>();
+
public View(Session session, int viewID, Type viewType)
{
this.session = session;
@@ -42,6 +49,26 @@ public class View implements IView
return viewID;
}
+ public void subscribe(CDOID id)
+ {
+ changeSubscriptionObjects.put(id, id);
+ }
+
+ public void unsubscribe(CDOID id)
+ {
+ changeSubscriptionObjects.remove(id);
+ }
+
+ public boolean isSubscribe(CDOID id)
+ {
+ return changeSubscriptionObjects.get(id) != null;
+ }
+
+ public void clearChangeSubscription()
+ {
+ changeSubscriptionObjects.clear();
+ }
+
public Type getViewType()
{
return viewType;
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/CDOServerProtocol.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/CDOServerProtocol.java
index 9d1821382c..2afe29cc70 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/CDOServerProtocol.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/CDOServerProtocol.java
@@ -11,6 +11,8 @@
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=233273
* Simon McDuff - 230832: Make remote invalidation configurable
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.internal.server.protocol;
@@ -88,9 +90,12 @@ public class CDOServerProtocol extends CDOProtocolImpl
case CDOProtocolConstants.SIGNAL_SYNC:
return new SyncRevisionIndication();
- case CDOProtocolConstants.SIGNAL_AUTOMATIC_REFRESH:
+ case CDOProtocolConstants.SIGNAL_PASSIVE_UPDATE:
return new PassiveUpdateIndication();
+ case CDOProtocolConstants.SIGNAL_CHANGE_SUBSCRIPTION:
+ return new ChangeSubscriptionIndication();
+
default:
return null;
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/ChangeSubscriptionIndication.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/ChangeSubscriptionIndication.java
new file mode 100644
index 0000000000..ca554f086b
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/ChangeSubscriptionIndication.java
@@ -0,0 +1,81 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.cdo.internal.server.protocol;
+
+import org.eclipse.emf.cdo.common.CDOProtocolConstants;
+import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.common.id.CDOIDObjectFactory;
+import org.eclipse.emf.cdo.common.id.CDOIDUtil;
+import org.eclipse.emf.cdo.internal.server.bundle.OM;
+import org.eclipse.emf.cdo.server.IView;
+
+import org.eclipse.net4j.util.io.ExtendedDataInputStream;
+import org.eclipse.net4j.util.io.ExtendedDataOutputStream;
+import org.eclipse.net4j.util.om.trace.ContextTracer;
+
+import java.io.IOException;
+
+/**
+ * @author Simon McDuff
+ */
+public class ChangeSubscriptionIndication extends CDOReadIndication
+{
+ private static final ContextTracer PROTOCOL = new ContextTracer(OM.DEBUG_PROTOCOL, ChangeSubscriptionIndication.class);
+
+ public ChangeSubscriptionIndication()
+ {
+ }
+
+ @Override
+ protected short getSignalID()
+ {
+ return CDOProtocolConstants.SIGNAL_CHANGE_SUBSCRIPTION;
+ }
+
+ @Override
+ protected void indicating(ExtendedDataInputStream in) throws IOException
+ {
+ CDOIDObjectFactory factory = getStore().getCDOIDObjectFactory();
+
+ int viewID = in.readInt();
+ boolean clear = in.readBoolean();
+
+ int size = in.readInt();
+ boolean registered = true;
+ if (size <= 0)
+ {
+ registered = false;
+ size = -size;
+ }
+
+ IView view = getSession().getView(viewID);
+
+ if (clear)
+ {
+ view.clearChangeSubscription();
+ }
+
+ for (int i = 0; i < size; i++)
+ {
+ CDOID id = CDOIDUtil.read(in, factory);
+ if (registered)
+ view.subscribe(id);
+ else
+ view.unsubscribe(id);
+ }
+ }
+
+ @Override
+ protected void responding(ExtendedDataOutputStream out) throws IOException
+ {
+ out.writeBoolean(true);
+ }
+}
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/InvalidationNotification.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/InvalidationNotification.java
index 1a6c64fa7d..44b23fb624 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/InvalidationNotification.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/InvalidationNotification.java
@@ -8,12 +8,16 @@
* Contributors:
* Eike Stepper - initial API and implementation
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=201266
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo.internal.server.protocol;
import org.eclipse.emf.cdo.common.CDOProtocolConstants;
import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.common.id.CDOIDProvider;
import org.eclipse.emf.cdo.common.id.CDOIDUtil;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
import org.eclipse.emf.cdo.internal.server.bundle.OM;
import org.eclipse.net4j.channel.IChannel;
@@ -31,15 +35,21 @@ public class InvalidationNotification extends Request
{
private static final ContextTracer PROTOCOL = new ContextTracer(OM.DEBUG_PROTOCOL, InvalidationNotification.class);
+ private CDOIDProvider provider;
+
private long timeStamp;
private List<CDOID> dirtyIDs;
+
+ private List<CDORevisionDelta> deltas;
- public InvalidationNotification(IChannel channel, long timeStamp, List<CDOID> dirtyIDs)
+ public InvalidationNotification(IChannel channel, CDOIDProvider provider, long timeStamp, List<CDOID> dirtyIDs, List<CDORevisionDelta> deltas)
{
super(channel);
+ this.provider = provider;
this.timeStamp = timeStamp;
this.dirtyIDs = dirtyIDs;
+ this.deltas = deltas;
}
@Override
@@ -62,10 +72,18 @@ public class InvalidationNotification extends Request
PROTOCOL.format("Writing {0} dirty IDs", dirtyIDs.size());
}
- out.writeInt(dirtyIDs.size());
+ out.writeInt(dirtyIDs == null ? 0 : dirtyIDs.size());
+
for (CDOID dirtyID : dirtyIDs)
{
CDOIDUtil.write(out, dirtyID);
}
+
+ out.writeInt(deltas == null ? 0 : deltas.size());
+
+ for (CDORevisionDelta delta : deltas)
+ {
+ delta.write(out, provider);
+ }
}
}
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/OpenSessionIndication.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/OpenSessionIndication.java
index 8c09b314f2..49b6930cc5 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/OpenSessionIndication.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/OpenSessionIndication.java
@@ -41,6 +41,8 @@ public class OpenSessionIndication extends IndicationWithResponse
private String repositoryName;
private boolean legacySupportEnabled;
+
+ private boolean passiveUpdateEnabled;
public OpenSessionIndication()
{
@@ -66,7 +68,13 @@ public class OpenSessionIndication extends IndicationWithResponse
{
PROTOCOL.format("Read legacySupportEnabled: {0}", legacySupportEnabled);
}
- }
+
+ passiveUpdateEnabled = in.readBoolean();
+ if (PROTOCOL.isEnabled())
+ {
+ PROTOCOL.format("Read passiveUpdateEnabled: {0}", passiveUpdateEnabled);
+ }
+}
@Override
protected void responding(ExtendedDataOutputStream out) throws IOException
@@ -78,6 +86,9 @@ public class OpenSessionIndication extends IndicationWithResponse
CDOServerProtocol serverProtocol = (CDOServerProtocol)getProtocol();
Session session = sessionManager.openSession(serverProtocol, legacySupportEnabled);
+
+ session.setPassiveUpdateEnabled(passiveUpdateEnabled);
+
serverProtocol.setInfraStructure(session);
writeSessionID(out, session);
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/PassiveUpdateIndication.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/PassiveUpdateIndication.java
index e9a061ba44..5920104409 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/PassiveUpdateIndication.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/internal/server/protocol/PassiveUpdateIndication.java
@@ -35,7 +35,7 @@ public class PassiveUpdateIndication extends SyncRevisionIndication
@Override
protected short getSignalID()
{
- return CDOProtocolConstants.SIGNAL_AUTOMATIC_REFRESH;
+ return CDOProtocolConstants.SIGNAL_PASSIVE_UPDATE;
}
@Override
protected void indicating(ExtendedDataInputStream in) throws IOException
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/INotificationManager.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/INotificationManager.java
new file mode 100644
index 0000000000..5bb5b84a16
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/INotificationManager.java
@@ -0,0 +1,24 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.cdo.server;
+
+import org.eclipse.emf.cdo.internal.server.Session;
+import org.eclipse.emf.cdo.server.IStoreWriter.CommitContext;
+
+/**
+ * @author Simon McDuff
+ */
+public interface INotificationManager
+{
+
+ public abstract void notifyInvalidation(Session session, CommitContext commitContext);
+
+}
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IRepository.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IRepository.java
index 89c5f7c7f4..c322ffb826 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IRepository.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IRepository.java
@@ -11,6 +11,7 @@
package org.eclipse.emf.cdo.server;
import org.eclipse.emf.cdo.common.id.CDOIDMetaRange;
+import org.eclipse.emf.cdo.internal.server.NotificationManager;
import org.eclipse.net4j.util.container.IContainer;
@@ -48,6 +49,8 @@ public interface IRepository extends IContainer<IRepositoryElement>
public IResourceManager getResourceManager();
public IRevisionManager getRevisionManager();
+
+ public INotificationManager getNotificationManager();
public long getLastMetaID();
diff --git a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IView.java b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IView.java
index d39dd0cdb4..b4b35e09e8 100644
--- a/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IView.java
+++ b/plugins/org.eclipse.emf.cdo.server/src/org/eclipse/emf/cdo/server/IView.java
@@ -11,6 +11,7 @@
package org.eclipse.emf.cdo.server;
import org.eclipse.emf.cdo.common.CDOProtocolView;
+import org.eclipse.emf.cdo.common.id.CDOID;
/**
* @author Eike Stepper
@@ -18,4 +19,7 @@ import org.eclipse.emf.cdo.common.CDOProtocolView;
public interface IView extends CDOProtocolView
{
public ISession getSession();
+ public void subscribe(CDOID id);
+ public void unsubscribe(CDOID id);
+ public void clearChangeSubscription();
}
diff --git a/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/AllTests.java b/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/AllTests.java
index feeb57cbe0..62611fe2e3 100644
--- a/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/AllTests.java
+++ b/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/AllTests.java
@@ -41,6 +41,8 @@ public class AllTests
suite.addTestSuite(IndexReconstructionTest.class);
suite.addTestSuite(NoLegacyTest.class);
suite.addTestSuite(SavePointTest.class);
+ suite.addTestSuite(ChangeSubscriptionTest.class);
+ suite.addTestSuite(QueryTest.class);
// TODO suite.addTestSuite(GeneratedEcoreTest.class);
// $JUnit-END$
diff --git a/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/ChangeSubscriptionTest.java b/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/ChangeSubscriptionTest.java
new file mode 100644
index 0000000000..09399015de
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo.tests/src/org/eclipse/emf/cdo/tests/ChangeSubscriptionTest.java
@@ -0,0 +1,575 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.cdo.tests;
+
+import org.eclipse.emf.cdo.CDOChangeSubscriptionPolicy;
+import org.eclipse.emf.cdo.CDONotification;
+import org.eclipse.emf.cdo.CDOSession;
+import org.eclipse.emf.cdo.CDOTransaction;
+import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.eresource.CDOResource;
+import org.eclipse.emf.cdo.tests.model1.Category;
+import org.eclipse.emf.cdo.tests.model1.Company;
+import org.eclipse.emf.cdo.tests.model1.Model1Factory;
+import org.eclipse.emf.cdo.tests.model1.Model1Package;
+
+import org.eclipse.emf.internal.cdo.InternalCDOObject;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.common.notify.Notifier;
+import org.eclipse.emf.ecore.EObject;
+
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+/**
+ * @author Simon McDuff
+ */
+public class ChangeSubscriptionTest extends AbstractCDOTest
+{
+ static class TestAdapter implements Adapter
+ {
+ List<Notification> notifications = new ArrayList<Notification>();
+
+ Notifier notifier;
+
+ public Notifier getTarget()
+ {
+ return notifier;
+ }
+
+ public List<Notification> getNotifications()
+ {
+ return notifications;
+ }
+
+ public boolean isAdapterForType(Object type)
+ {
+ return false;
+ }
+
+ public void notifyChanged(Notification notification)
+ {
+ notifications.add(notification);
+ }
+
+ public void setTarget(Notifier newTarget)
+ {
+ this.notifier = newTarget;
+ }
+
+ }
+
+ public void testSameSession() throws Exception
+ {
+ testSameSession(CDOChangeSubscriptionPolicy.ALL);
+ }
+
+ public void testSameSession_disable() throws Exception
+ {
+ testSameSession(CDOChangeSubscriptionPolicy.NONE);
+ }
+
+ public void testSameSession(final CDOChangeSubscriptionPolicy enabled) throws Exception
+ {
+ msg("Opening session");
+ final CDOSession session = openModel1Session();
+
+ session.setPassiveUpdateEnabled(false);
+
+ // ************************************************************* //
+
+ msg("Creating category1");
+ final Category category1A = Model1Factory.eINSTANCE.createCategory();
+ category1A.setName("category1");
+
+ msg("Creating company");
+ final Company companyA = Model1Factory.eINSTANCE.createCompany();
+
+ msg("Adding categories");
+ companyA.getCategories().add(category1A);
+
+ msg("Opening transaction");
+ final CDOTransaction transaction = session.openTransaction();
+
+ transaction.setChangeSubscriptionPolicy(enabled);
+
+ msg("Creating resource");
+ final CDOResource resourceA = transaction.createResource("/test1");
+
+ msg("Adding company");
+ resourceA.getContents().add(companyA);
+
+ msg("Committing");
+ transaction.commit();
+ final TestAdapter adapter = new TestAdapter();
+ category1A.eAdapters().add(adapter);
+
+ // ************************************************************* //
+
+ msg("Opening view");
+ final CDOTransaction transaction2 = session.openTransaction();
+
+ final Category category1B = (Category)transaction2.getObject(category1A.cdoID(), true);
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ boolean timedOut = new PollingTimeOuter(10, 100)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return (enabled == CDOChangeSubscriptionPolicy.ALL && adapter.getNotifications().size() == 1)
+ || (enabled == CDOChangeSubscriptionPolicy.NONE && adapter.getNotifications().size() == 0);
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+
+ // Switching policy to the other
+ final CDOChangeSubscriptionPolicy enabled2 = enabled == CDOChangeSubscriptionPolicy.ALL ? CDOChangeSubscriptionPolicy.NONE
+ : CDOChangeSubscriptionPolicy.ALL;
+
+ transaction.setChangeSubscriptionPolicy(enabled2);
+
+ adapter.getNotifications().clear();
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME_VERSION 2");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ timedOut = new PollingTimeOuter(10, 100)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return (enabled2 == CDOChangeSubscriptionPolicy.ALL && adapter.getNotifications().size() == 1)
+ || (enabled2 == CDOChangeSubscriptionPolicy.NONE && adapter.getNotifications().size() == 0);
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+ }
+
+ public void testSeparateSession() throws Exception
+ {
+ testSeparateSession(CDOChangeSubscriptionPolicy.ALL);
+
+ }
+
+ public void testSeparateSession_disable() throws Exception
+ {
+ testSeparateSession(CDOChangeSubscriptionPolicy.NONE);
+ }
+
+ public void testSeparateSession(final CDOChangeSubscriptionPolicy enabled) throws Exception
+ {
+ msg("Opening session");
+ final CDOSession session = openModel1Session();
+
+ session.setPassiveUpdateEnabled(false);
+
+ // ************************************************************* //
+
+ msg("Creating category1");
+ final Category category1A = Model1Factory.eINSTANCE.createCategory();
+ category1A.setName("category1");
+
+ msg("Creating company");
+ final Company companyA = Model1Factory.eINSTANCE.createCompany();
+
+ msg("Adding categories");
+ companyA.getCategories().add(category1A);
+
+ msg("Opening transaction");
+ final CDOTransaction transaction = session.openTransaction();
+ transaction.setChangeSubscriptionPolicy(enabled);
+
+ msg("Creating resource");
+ final CDOResource resourceA = transaction.createResource("/test1");
+
+ msg("Adding company");
+ resourceA.getContents().add(companyA);
+
+ msg("Committing");
+ transaction.commit();
+ final TestAdapter adapter = new TestAdapter();
+ category1A.eAdapters().add(adapter);
+
+ // ************************************************************* //
+
+ msg("Opening view");
+ final CDOSession session2 = openModel1Session();
+ session2.setPassiveUpdateEnabled(false);
+
+ final CDOTransaction transaction2 = session2.openTransaction();
+
+ final Category category1B = (Category)transaction2.getObject(category1A.cdoID(), true);
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ boolean timedOut = new PollingTimeOuter(10, 100)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return (enabled == CDOChangeSubscriptionPolicy.ALL && adapter.getNotifications().size() == 1)
+ || (enabled == CDOChangeSubscriptionPolicy.NONE && adapter.getNotifications().size() == 0);
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+
+ // Switching policy to the other
+ final CDOChangeSubscriptionPolicy enabled2 = enabled == CDOChangeSubscriptionPolicy.ALL ? CDOChangeSubscriptionPolicy.NONE
+ : CDOChangeSubscriptionPolicy.ALL;
+
+ transaction.setChangeSubscriptionPolicy(enabled2);
+
+ adapter.getNotifications().clear();
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME_VERSION 2");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ timedOut = new PollingTimeOuter(10, 100)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return (enabled2 == CDOChangeSubscriptionPolicy.ALL && adapter.getNotifications().size() == 1)
+ || (enabled2 == CDOChangeSubscriptionPolicy.NONE && adapter.getNotifications().size() == 0);
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+
+ }
+
+ public void testTemporaryObject() throws Exception
+ {
+ msg("Opening session");
+ final CDOSession session = openModel1Session();
+
+ session.setPassiveUpdateEnabled(false);
+
+ // ************************************************************* //
+
+ msg("Creating category1");
+ final Category category1A = Model1Factory.eINSTANCE.createCategory();
+ category1A.setName("category1");
+
+ msg("Creating company");
+ final Company companyA = Model1Factory.eINSTANCE.createCompany();
+
+ msg("Adding categories");
+ companyA.getCategories().add(category1A);
+
+ msg("Opening transaction");
+ final CDOTransaction transaction = session.openTransaction();
+ transaction.setChangeSubscriptionPolicy(CDOChangeSubscriptionPolicy.ALL);
+ msg("Creating resource");
+ final CDOResource resourceA = transaction.createResource("/test1");
+
+ msg("Adding company");
+ resourceA.getContents().add(companyA);
+
+ msg("Committing");
+
+ final TestAdapter adapter = new TestAdapter();
+ category1A.eAdapters().add(adapter);
+
+ transaction.commit();
+
+ // ************************************************************* //
+
+ msg("Opening view");
+ final CDOSession session2 = openModel1Session();
+ session2.setPassiveUpdateEnabled(false);
+
+ final CDOTransaction transaction2 = session2.openTransaction();
+ transaction.setChangeSubscriptionPolicy(CDOChangeSubscriptionPolicy.ALL);
+
+ final Category category1B = (Category)transaction2.getObject(category1A.cdoID(), true);
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ boolean timedOut = new PollingTimeOuter(10, 100)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return adapter.getNotifications().size() == 1;
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+ }
+
+ class CDOIDFilterChangeSubscriptionPolicy implements CDOChangeSubscriptionPolicy
+ {
+ private Set<CDOID> cdoIDs = new HashSet<CDOID>();
+
+ public boolean valid(EObject eObject, Adapter object)
+ {
+ return cdoIDs.contains(((InternalCDOObject)eObject).cdoID());
+ }
+
+ public Set<CDOID> getCdoIDs()
+ {
+ return cdoIDs;
+ }
+ }
+
+ public void testSeparateSession_CUSTOM() throws Exception
+ {
+
+ CDOIDFilterChangeSubscriptionPolicy customPolicy = new CDOIDFilterChangeSubscriptionPolicy();
+
+ msg("Opening session");
+ final CDOSession session = openModel1Session();
+
+ session.setPassiveUpdateEnabled(false);
+
+ // ************************************************************* //
+
+ msg("Creating category1");
+ final Category category1A = Model1Factory.eINSTANCE.createCategory();
+ category1A.setName("category1");
+
+ msg("Creating company");
+ final Company companyA = Model1Factory.eINSTANCE.createCompany();
+
+ msg("Adding categories");
+ companyA.getCategories().add(category1A);
+
+ msg("Opening transaction");
+ final CDOTransaction transaction = session.openTransaction();
+
+ transaction.setChangeSubscriptionPolicy(customPolicy);
+
+ msg("Creating resource");
+ final CDOResource resourceA = transaction.createResource("/test1");
+
+ msg("Adding company");
+ resourceA.getContents().add(companyA);
+
+ msg("Committing");
+ transaction.commit();
+
+ final TestAdapter adapter = new TestAdapter();
+
+ customPolicy.getCdoIDs().add(category1A.cdoID());
+
+ category1A.eAdapters().add(adapter);
+ companyA.eAdapters().add(adapter);
+
+ // ************************************************************* //
+
+ msg("Opening view");
+ final CDOSession session2 = openModel1Session();
+ session2.setPassiveUpdateEnabled(false);
+
+ final CDOTransaction transaction2 = session2.openTransaction();
+
+ final Category category1B = (Category)transaction2.getObject(category1A.cdoID(), true);
+ final Company company1B = (Company)transaction2.getObject(companyA.cdoID(), true);
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME");
+ company1B.setName("TEST1");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ boolean timedOut = new PollingTimeOuter(5, 200)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return adapter.getNotifications().size() == 1;
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+
+ // Switching policy to the other
+ transaction.setChangeSubscriptionPolicy(CDOChangeSubscriptionPolicy.ALL);
+
+ adapter.getNotifications().clear();
+
+ msg("Changing name");
+ category1B.setName("CHANGED NAME_VERSION 2");
+ company1B.setName("TEST2");
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ timedOut = new PollingTimeOuter(10, 100)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return adapter.getNotifications().size() == 2;
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+
+ }
+
+ public void testNotificationChain() throws Exception
+ {
+ msg("Opening session");
+ final CDOSession session = openModel1Session();
+
+ session.setPassiveUpdateEnabled(false);
+
+ // ************************************************************* //
+
+ msg("Creating category1");
+ final Category category1A = Model1Factory.eINSTANCE.createCategory();
+ category1A.setName("category1");
+
+ msg("Creating company");
+ final Company companyA = Model1Factory.eINSTANCE.createCompany();
+
+ msg("Adding categories");
+ companyA.getCategories().add(category1A);
+
+ msg("Opening transaction");
+ final CDOTransaction transaction = session.openTransaction();
+
+ transaction.setChangeSubscriptionPolicy(CDOChangeSubscriptionPolicy.ALL);
+
+ msg("Creating resource");
+ final CDOResource resourceA = transaction.createResource("/test1");
+
+ msg("Adding company");
+ resourceA.getContents().add(companyA);
+
+ msg("Committing");
+ transaction.commit();
+
+ final TestAdapter adapter = new TestAdapter();
+
+ companyA.eAdapters().add(adapter);
+
+ // ************************************************************* //
+
+ msg("Opening view");
+ final CDOSession session2 = openModel1Session();
+ session2.setPassiveUpdateEnabled(false);
+
+ final CDOTransaction transaction2 = session2.openTransaction();
+
+ final Company company1B = (Company)transaction2.getObject(companyA.cdoID(), true);
+
+ msg("Changing name");
+ company1B.setName("TEST1");
+ company1B.setCity("CITY1");
+
+ final Category category2B = Model1Factory.eINSTANCE.createCategory();
+ company1B.getCategories().add(category2B);
+
+ assertEquals(0, adapter.getNotifications().size());
+
+ msg("Committing");
+ transaction2.commit();
+
+ msg("Checking after commit");
+ boolean timedOut = new PollingTimeOuter(5, 200)
+ {
+ @Override
+ protected boolean successful()
+ {
+ return adapter.getNotifications().size() == 3;
+ }
+ }.timedOut();
+
+ assertEquals(false, timedOut);
+ int count = 0;
+ for (Notification notification : adapter.getNotifications())
+ {
+ CDONotification cdoNotification = (CDONotification)notification;
+
+ if (adapter.getNotifications().size() - 1 == count)
+ assertEquals(false,cdoNotification.hasNext());
+ else
+ assertEquals(true,cdoNotification.hasNext());
+
+
+ if (notification.getFeature() == Model1Package.eINSTANCE.getCategory_Name())
+ {
+ assertEquals(Notification.SET, notification.getEventType());
+ assertEquals("TEST1", notification.getNewStringValue());
+ }
+ else if (notification.getFeature() == Model1Package.eINSTANCE.getAddress_City())
+ {
+ assertEquals(Notification.SET, notification.getEventType());
+ assertEquals("CITY1", notification.getNewStringValue());
+ }
+ else if (notification.getFeature() == Model1Package.eINSTANCE.getCompany_Categories())
+ {
+ assertEquals(Notification.ADD, notification.getEventType());
+ assertEquals(1, notification.getPosition());
+ assertEquals(transaction.getObject(category2B.cdoID(), true), notification.getNewValue());
+
+ }
+ else
+ assertEquals(false, false);
+
+ count++;
+
+ }
+
+ }
+}
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOChangeSubscriptionPolicy.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOChangeSubscriptionPolicy.java
new file mode 100644
index 0000000000..ad727af420
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOChangeSubscriptionPolicy.java
@@ -0,0 +1,38 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.cdo;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.ecore.EObject;
+
+/**
+ * @author Simon McDuff
+ */
+public interface CDOChangeSubscriptionPolicy
+{
+ public static CDOChangeSubscriptionPolicy NONE = new CDOChangeSubscriptionPolicy()
+ {
+ public boolean valid(EObject eObject, Adapter adapter)
+ {
+ return false;
+ }
+ };
+
+ public static CDOChangeSubscriptionPolicy ALL = new CDOChangeSubscriptionPolicy()
+ {
+ public boolean valid(EObject eObject, Adapter adapter)
+ {
+ return true;
+ }
+ };
+
+ boolean valid(EObject eObject, Adapter adapter);
+}
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDONotification.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDONotification.java
new file mode 100644
index 0000000000..d88f6cd894
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDONotification.java
@@ -0,0 +1,26 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.cdo;
+
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
+
+import org.eclipse.emf.common.notify.Notification;
+
+/**
+ * @author Simon McDuff
+ */
+public interface CDONotification extends Notification
+{
+ boolean hasNext();
+
+ public CDORevisionDelta getRevisionDelta();
+
+}
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOView.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOView.java
index 6cebdbe5f8..2fbcec0f1a 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOView.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/cdo/CDOView.java
@@ -9,6 +9,8 @@
* Eike Stepper - initial API and implementation
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=201266
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=201997
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.cdo;
@@ -60,6 +62,10 @@ public interface CDOView extends CDOProtocolView, INotifier
public void setInvalidationNotificationsEnabled(boolean invalidationNotificationsEnabled);
+ public CDOChangeSubscriptionPolicy getChangeSubscriptionPolicy();
+
+ public void setChangeSubscriptionPolicy(CDOChangeSubscriptionPolicy changeSubscriptionPolicy);
+
public int getLoadRevisionCollectionChunkSize();
public void setLoadRevisionCollectionChunkSize(int loadRevisionCollectionChunkSize);
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationBuilder.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationBuilder.java
new file mode 100644
index 0000000000..0b3cc3dbb6
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationBuilder.java
@@ -0,0 +1,130 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.internal.cdo;
+
+import org.eclipse.emf.cdo.common.revision.delta.CDOAddFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOClearFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOContainerFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOFeatureDeltaVisitor;
+import org.eclipse.emf.cdo.common.revision.delta.CDOListFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOMoveFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDORemoveFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOSetFeatureDelta;
+import org.eclipse.emf.cdo.common.revision.delta.CDOUnsetFeatureDelta;
+import org.eclipse.emf.cdo.util.CDOPackageRegistry;
+
+import org.eclipse.emf.internal.cdo.util.ModelUtil;
+
+import org.eclipse.emf.common.notify.impl.NotificationImpl;
+import org.eclipse.emf.ecore.EStructuralFeature;
+import org.eclipse.emf.ecore.InternalEObject;
+
+/**
+ * @author Simon McDuff
+ */
+public class CDONotificationBuilder implements CDOFeatureDeltaVisitor
+{
+ private NotificationImpl notification = null;
+
+ private CDORevisionDelta delta = null;
+
+ private InternalEObject internalObject = null;
+
+ private CDOPackageRegistry packageRegistry = null;
+
+ public CDONotificationBuilder(CDOPackageRegistry packageRegistry)
+ {
+ this.packageRegistry = packageRegistry;
+ }
+
+ synchronized public NotificationImpl buildNotification(InternalEObject internalObject, CDORevisionDelta delta)
+ {
+ notification = null;
+ this.internalObject = internalObject;
+ this.delta = delta;
+ delta.accept(this);
+
+ return notification;
+ }
+
+ protected void add(CDONotificationImpl newNotificaton)
+ {
+ newNotificaton.setRevisionDelta(delta);
+
+ if (notification == null)
+ notification = newNotificaton;
+ else
+ notification.add(newNotificaton);
+ }
+
+ public void visit(CDOMoveFeatureDelta delta)
+ {
+ EStructuralFeature eFeature = ModelUtil.getEFeature(delta.getFeature(), packageRegistry);
+
+ int oldPosition = delta.getOldPosition();
+ int newPosition = delta.getNewPosition();
+
+ add(new CDONotificationImpl(internalObject, NotificationImpl.MOVE, eFeature.getFeatureID(),
+ new Integer(oldPosition), null, newPosition));
+ }
+
+ public void visit(CDOAddFeatureDelta delta)
+ {
+ EStructuralFeature eFeature = ModelUtil.getEFeature(delta.getFeature(), packageRegistry);
+
+ add(new CDONotificationImpl(internalObject, NotificationImpl.ADD, eFeature.getFeatureID(), null, delta.getValue(),
+ delta.getIndex()));
+ }
+
+ public void visit(CDORemoveFeatureDelta delta)
+ {
+ EStructuralFeature eFeature = ModelUtil.getEFeature(delta.getFeature(), packageRegistry);
+
+ add(new CDONotificationImpl(internalObject, NotificationImpl.REMOVE, eFeature.getFeatureID(), null, null, delta
+ .getIndex()));
+ }
+
+ public void visit(CDOSetFeatureDelta delta)
+ {
+ EStructuralFeature eFeature = ModelUtil.getEFeature(delta.getFeature(), packageRegistry);
+
+ add(new CDONotificationImpl(internalObject, NotificationImpl.SET, eFeature.getFeatureID(), null, delta.getValue()));
+ }
+
+ public void visit(CDOUnsetFeatureDelta delta)
+ {
+ EStructuralFeature eFeature = ModelUtil.getEFeature(delta.getFeature(), packageRegistry);
+
+ add(new CDONotificationImpl(internalObject, NotificationImpl.UNSET, eFeature.getFeatureID(), null, null));
+
+ }
+
+ public void visit(CDOListFeatureDelta deltas)
+ {
+ for (CDOFeatureDelta delta : deltas.getListChanges())
+ delta.accept(this);
+ }
+
+ public void visit(CDOClearFeatureDelta delta)
+ {
+ EStructuralFeature eFeature = ModelUtil.getEFeature(delta.getFeature(), packageRegistry);
+
+ add(new CDONotificationImpl(internalObject, NotificationImpl.SET, eFeature.getFeatureID(), null, null));
+ }
+
+ public void visit(CDOContainerFeatureDelta delta)
+ {
+
+ }
+
+}
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationImpl.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationImpl.java
new file mode 100644
index 0000000000..06dbe04db5
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDONotificationImpl.java
@@ -0,0 +1,212 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ **************************************************************************/
+package org.eclipse.emf.internal.cdo;
+
+import org.eclipse.emf.cdo.CDONotification;
+import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
+
+import org.eclipse.emf.ecore.EStructuralFeature;
+import org.eclipse.emf.ecore.InternalEObject;
+import org.eclipse.emf.ecore.impl.ENotificationImpl;
+
+/**
+ * @author Simon McDuff
+ */
+public class CDONotificationImpl extends ENotificationImpl implements CDONotification
+{
+ private CDORevisionDelta revisionDelta = null;
+
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, EStructuralFeature feature, Object oldValue,
+ Object newValue, boolean isSetChange)
+ {
+ super(notifier, eventType, feature, oldValue, newValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, EStructuralFeature feature, Object oldValue,
+ Object newValue, int position, boolean wasSet)
+ {
+ super(notifier, eventType, feature, oldValue, newValue, position, wasSet);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, EStructuralFeature feature, Object oldValue,
+ Object newValue, int position)
+ {
+ super(notifier, eventType, feature, oldValue, newValue, position);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, EStructuralFeature feature, Object oldValue,
+ Object newValue)
+ {
+ super(notifier, eventType, feature, oldValue, newValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, boolean oldBooleanValue,
+ boolean newBooleanValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldBooleanValue, newBooleanValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, boolean oldBooleanValue,
+ boolean newBooleanValue)
+ {
+ super(notifier, eventType, featureID, oldBooleanValue, newBooleanValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, byte oldByteValue,
+ byte newByteValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldByteValue, newByteValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, byte oldByteValue,
+ byte newByteValue)
+ {
+ super(notifier, eventType, featureID, oldByteValue, newByteValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, char oldCharValue,
+ char newCharValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldCharValue, newCharValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, char oldCharValue,
+ char newCharValue)
+ {
+ super(notifier, eventType, featureID, oldCharValue, newCharValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, double oldDoubleValue,
+ double newDoubleValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldDoubleValue, newDoubleValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, double oldDoubleValue,
+ double newDoubleValue)
+ {
+ super(notifier, eventType, featureID, oldDoubleValue, newDoubleValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, float oldFloatValue,
+ float newFloatValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldFloatValue, newFloatValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, float oldFloatValue,
+ float newFloatValue)
+ {
+ super(notifier, eventType, featureID, oldFloatValue, newFloatValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, int oldIntValue, int newIntValue,
+ boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldIntValue, newIntValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, int oldIntValue, int newIntValue)
+ {
+ super(notifier, eventType, featureID, oldIntValue, newIntValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, long oldLongValue,
+ long newLongValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldLongValue, newLongValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, long oldLongValue,
+ long newLongValue)
+ {
+ super(notifier, eventType, featureID, oldLongValue, newLongValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, Object oldValue, Object newValue,
+ boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldValue, newValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, Object oldValue, Object newValue,
+ int position, boolean wasSet)
+ {
+ super(notifier, eventType, featureID, oldValue, newValue, position, wasSet);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, Object oldValue, Object newValue,
+ int position)
+ {
+ super(notifier, eventType, featureID, oldValue, newValue, position);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, Object oldValue, Object newValue)
+ {
+ super(notifier, eventType, featureID, oldValue, newValue);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, short oldShortValue,
+ short newShortValue, boolean isSetChange)
+ {
+ super(notifier, eventType, featureID, oldShortValue, newShortValue, isSetChange);
+ }
+
+ public CDONotificationImpl(InternalEObject notifier, int eventType, int featureID, short oldShortValue,
+ short newShortValue)
+ {
+ super(notifier, eventType, featureID, oldShortValue, newShortValue);
+ }
+ private InternalCDOObject getCDOObject()
+ {
+ return (InternalCDOObject) getNotifier();
+ }
+ @Override
+ public Object getNewValue()
+ {
+ Object object = super.getNewValue();
+
+ return adapt(object);
+ }
+
+ @Override
+ public Object getOldValue()
+ {
+ return adapt(super.getOldValue());
+ }
+
+ public Object adapt(Object object)
+ {
+ if (object instanceof CDOID)
+ {
+ object = getCDOObject().cdoView().getObject((CDOID)object, true);
+ }
+ return object;
+ }
+
+ public boolean hasNext()
+ {
+ return next != null;
+ }
+
+ public CDORevisionDelta getRevisionDelta()
+ {
+ return revisionDelta;
+ }
+
+ public void setRevisionDelta(CDORevisionDelta revisionDelta)
+ {
+ this.revisionDelta = revisionDelta;
+ }
+
+}
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOObjectImpl.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOObjectImpl.java
index cc76599b02..83f66c71f4 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOObjectImpl.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOObjectImpl.java
@@ -7,6 +7,8 @@
*
* Contributors:
* Eike Stepper - initial API and implementation
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.internal.cdo;
@@ -29,6 +31,7 @@ import org.eclipse.emf.internal.cdo.util.ModelUtil;
import org.eclipse.net4j.util.ImplementationError;
import org.eclipse.net4j.util.om.trace.ContextTracer;
+import org.eclipse.emf.common.notify.Adapter;
import org.eclipse.emf.common.util.BasicEMap;
import org.eclipse.emf.common.util.ECollections;
import org.eclipse.emf.common.util.EList;
@@ -214,6 +217,14 @@ public class CDOObjectImpl extends EStoreEObjectImpl implements InternalCDOObjec
}
}
}
+ if (eBasicAdapters() != null)
+ {
+ for (Adapter adapter : eBasicAdapters())
+ {
+ cdoView().subscribe(this, adapter);
+ }
+ }
+
}
@SuppressWarnings("unchecked")
@@ -359,6 +370,37 @@ public class CDOObjectImpl extends EStoreEObjectImpl implements InternalCDOObjec
{
return eDynamicFeature(dynamicFeatureID);
}
+
+ @Override
+ public EList<Adapter> eAdapters()
+ {
+ if (eAdapters == null)
+ {
+ eAdapters = new EAdapterList<Adapter>(this)
+ {
+ private static final long serialVersionUID = 1L;
+
+ @Override
+ protected void didAdd(int index, Adapter newObject)
+ {
+ if (!FSMUtil.isTransient(CDOObjectImpl.this))
+ {
+ cdoView().subscribe(CDOObjectImpl.this, newObject);
+ }
+ }
+
+ @Override
+ protected void didRemove(int index, Adapter oldObject)
+ {
+ if (!FSMUtil.isTransient(CDOObjectImpl.this))
+ {
+ cdoView().unsubscribe(CDOObjectImpl.this, oldObject);
+ }
+ }
+ };
+ }
+ return eAdapters;
+ }
@Override
protected FeatureMap createFeatureMap(EStructuralFeature eStructuralFeature)
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOSessionImpl.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOSessionImpl.java
index 74da7fa192..b1825d37f9 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOSessionImpl.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOSessionImpl.java
@@ -10,6 +10,8 @@
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=226778
* Simon McDuff - 230832: Make remote invalidation configurable
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.internal.cdo;
@@ -28,6 +30,7 @@ import org.eclipse.emf.cdo.common.model.CDOClass;
import org.eclipse.emf.cdo.common.model.CDOClassRef;
import org.eclipse.emf.cdo.common.model.CDOPackage;
import org.eclipse.emf.cdo.common.revision.CDORevision;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
import org.eclipse.emf.cdo.common.util.TransportException;
import org.eclipse.emf.cdo.util.CDOPackageRegistry;
import org.eclipse.emf.cdo.util.CDOUtil;
@@ -555,19 +558,23 @@ public class CDOSessionImpl extends Container<CDOView> implements CDOSession, CD
types.put(id, type);
}
- public void notifyInvalidation(long timeStamp, Set<CDOID> dirtyOIDs, CDOViewImpl excludedView)
+ public void notifyCommit(long timeStamp, Set<CDOID> dirtyOIDs, Collection<CDORevisionDelta> deltas,
+ CDOViewImpl excludedView)
{
- if (!isPassiveUpdateEnabled()) return;
+ if (isPassiveUpdateEnabled())
+ {
+ notifyInvalidation(timeStamp, dirtyOIDs, excludedView);
+ }
- forceNotifyInvalidation(timeStamp, dirtyOIDs, excludedView);
+ notifyChangeSubcription(deltas, excludedView);
}
- public void refresh(Set<CDOID> dirtyOIDs)
+ public void notifySync(Set<CDOID> dirtyOIDs)
{
- forceNotifyInvalidation(CDORevision.UNSPECIFIED_DATE, dirtyOIDs, null);
+ notifyInvalidation(CDORevision.UNSPECIFIED_DATE, dirtyOIDs, null);
}
- private void forceNotifyInvalidation(long timeStamp, Set<CDOID> dirtyOIDs, CDOViewImpl excludedView)
+ private void notifyInvalidation(long timeStamp, Set<CDOID> dirtyOIDs, CDOViewImpl excludedView)
{
dirtyOIDs = Collections.unmodifiableSet(dirtyOIDs);
@@ -589,6 +596,26 @@ public class CDOSessionImpl extends Container<CDOView> implements CDOSession, CD
fireInvalidationEvent(timeStamp, dirtyOIDs, excludedView);
}
+ private void notifyChangeSubcription(Collection<CDORevisionDelta> deltas, CDOViewImpl excludedView)
+ {
+ if (deltas == null || deltas.size() <= 0) return;
+
+ for (CDOViewImpl view : getViews())
+ {
+ if (view != excludedView)
+ {
+ try
+ {
+ view.notifyChangeSubcription(deltas);
+ }
+ catch (RuntimeException ex)
+ {
+ OM.LOG.error(ex);
+ }
+ }
+ }
+ }
+
public void fireInvalidationEvent(long timeStamp, Set<CDOID> dirtyOIDs, CDOViewImpl excludedView)
{
fireEvent(new InvalidationEvent(excludedView, timeStamp, dirtyOIDs));
@@ -698,7 +725,8 @@ public class CDOSessionImpl extends Container<CDOView> implements CDOSession, CD
channel = connector.openChannel(CDOProtocolConstants.PROTOCOL_NAME, this);
}
- OpenSessionRequest request = new OpenSessionRequest(channel, repositoryName, legacySupportEnabled);
+ OpenSessionRequest request = new OpenSessionRequest(channel, repositoryName, legacySupportEnabled,
+ passiveUpdateEnabled);
OpenSessionResult result = request.send();
sessionID = result.getSessionID();
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOTransactionImpl.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOTransactionImpl.java
index 6e1cff523f..3b6bd62272 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOTransactionImpl.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOTransactionImpl.java
@@ -10,6 +10,8 @@
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=201266
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=233314
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=215688
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.internal.cdo;
@@ -208,6 +210,8 @@ public class CDOTransactionImpl extends CDOViewImpl implements CDOTransaction
{
newPackages = analyzeNewPackages();
+ Collection<CDORevisionDelta> deltas = getRevisionDeltas().values();
+
for (CDOSavePointImpl itrSavePoint = lastSavePoint; itrSavePoint != null; itrSavePoint = itrSavePoint
.getPreviousSavePoint())
{
@@ -239,15 +243,19 @@ public class CDOTransactionImpl extends CDOViewImpl implements CDOTransaction
((InternalCDOPackage)newPackage).setPersistent(true);
}
+ changeSubscriptionManager.notifyCommit();
+
Map<CDOID, CDOObject> dirtyObjects = this.getDirtyObjects();
if (!dirtyObjects.isEmpty())
{
- session.notifyInvalidation(result.getTimeStamp(), dirtyObjects.keySet(), this);
+ session.notifyCommit(result.getTimeStamp(), dirtyObjects.keySet(),deltas, this);
}
cleanUp();
Map<CDOIDTemp, CDOID> idMappings = result.getIDMappings();
+
+
fireEvent(new FinishedEvent(CDOTransactionFinishedEvent.Type.COMMITTED, idMappings));
}
catch (RuntimeException ex)
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOViewImpl.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOViewImpl.java
index 6a781b53ee..76b0ce733b 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOViewImpl.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/CDOViewImpl.java
@@ -13,9 +13,12 @@
* Simon McDuff - https://bugs.eclipse.org/bugs/show_bug.cgi?id=202064
* Simon McDuff - 230832: Make remote invalidation configurable
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.internal.cdo;
+import org.eclipse.emf.cdo.CDOChangeSubscriptionPolicy;
import org.eclipse.emf.cdo.CDOObject;
import org.eclipse.emf.cdo.CDOState;
import org.eclipse.emf.cdo.CDOView;
@@ -29,6 +32,8 @@ import org.eclipse.emf.cdo.common.id.CDOIDProvider;
import org.eclipse.emf.cdo.common.model.CDOClass;
import org.eclipse.emf.cdo.common.model.CDOClassRef;
import org.eclipse.emf.cdo.common.revision.CDORevisionResolver;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
+import org.eclipse.emf.cdo.common.util.CDOException;
import org.eclipse.emf.cdo.common.util.TransportException;
import org.eclipse.emf.cdo.eresource.CDOResource;
import org.eclipse.emf.cdo.eresource.EresourceFactory;
@@ -40,6 +45,7 @@ import org.eclipse.emf.cdo.util.CDOUtil;
import org.eclipse.emf.cdo.util.ReadOnlyException;
import org.eclipse.emf.internal.cdo.bundle.OM;
+import org.eclipse.emf.internal.cdo.protocol.ChangeSubscriptionRequest;
import org.eclipse.emf.internal.cdo.protocol.ResourceIDRequest;
import org.eclipse.emf.internal.cdo.protocol.ResourcePathRequest;
import org.eclipse.emf.internal.cdo.query.CDOQueryImpl;
@@ -55,6 +61,7 @@ import org.eclipse.net4j.util.transaction.TransactionException;
import org.eclipse.emf.common.notify.Adapter;
import org.eclipse.emf.common.notify.Notification;
import org.eclipse.emf.common.notify.Notifier;
+import org.eclipse.emf.common.notify.impl.NotificationImpl;
import org.eclipse.emf.common.util.EList;
import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.EClass;
@@ -71,6 +78,8 @@ import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Set;
+import java.util.Map.Entry;
+import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
/**
@@ -103,6 +112,10 @@ public class CDOViewImpl extends org.eclipse.net4j.util.event.Notifier implement
private InternalCDOObject lastLookupObject;
+ protected ChangeSubscriptionManager changeSubscriptionManager = new ChangeSubscriptionManager();
+
+ protected CDOChangeSubscriptionPolicy changeSubscriptionPolicy = CDOChangeSubscriptionPolicy.NONE;
+
public CDOViewImpl(int id, CDOSessionImpl session)
{
viewID = id;
@@ -112,6 +125,187 @@ public class CDOViewImpl extends org.eclipse.net4j.util.event.Notifier implement
objects = createObjectsMap();
}
+ public class ChangeSubscriptionManager
+ {
+ // List of persisted objects
+ private Map<InternalCDOObject, Integer> persistedObjects = new ConcurrentHashMap<InternalCDOObject, Integer>();
+
+ // List of new objects
+ private Map<InternalCDOObject, Integer> newObjects = new ConcurrentHashMap<InternalCDOObject, Integer>();
+
+ private boolean valid(InternalCDOObject internalCDOObject)
+ {
+ return !internalCDOObject.cdoID().isTemporary();
+ }
+
+ protected int getNumberOfValidAdapter(InternalCDOObject object)
+ {
+ int count = 0;
+ if (object.eNotificationRequired())
+ {
+ for (Adapter adapter : object.eAdapters())
+ {
+ if (changeSubscriptionPolicy.valid(object, adapter)) count++;
+ }
+
+ }
+ return count;
+ }
+
+ /*
+ * Register to the server all objects from the active list
+ */
+ protected void notifyChangeSubcriptionPolicy()
+ {
+ synchronized (persistedObjects)
+ {
+ persistedObjects.clear();
+ newObjects.clear();
+
+ List<CDOID> cdoIDs = new ArrayList<CDOID>();
+
+ if (changeSubscriptionPolicy != CDOChangeSubscriptionPolicy.NONE)
+ {
+ for (InternalCDOObject cdoObject : objects.values())
+ {
+ int count = getNumberOfValidAdapter(cdoObject);
+
+ if (count > 0)
+ {
+ cdoIDs.add(cdoObject.cdoID());
+ boolean isValid = valid(cdoObject);
+ Map<InternalCDOObject, Integer> subscribersMap = isValid ? persistedObjects : newObjects;
+ subscribersMap.put(cdoObject, count);
+ }
+ }
+ }
+ request(cdoIDs, true, true);
+ }
+ }
+
+ protected void request(List<CDOID> cdoIDs, boolean registered, boolean clear)
+ {
+ try
+ {
+ new ChangeSubscriptionRequest(getSession().getChannel(), getViewID(), cdoIDs, registered, clear).send();
+ }
+ catch (Exception ex)
+ {
+ throw new TransactionException(ex);
+ }
+ }
+
+ protected void notifyCommit()
+ {
+ synchronized (persistedObjects)
+ {
+ List<InternalCDOObject> objectToRemove = new ArrayList<InternalCDOObject>();
+ for (Entry<InternalCDOObject, Integer> entry : newObjects.entrySet())
+ {
+ if (valid(entry.getKey()))
+ {
+ subscribe(entry.getKey(), entry.getValue());
+ objectToRemove.add(entry.getKey());
+ }
+ }
+ for (InternalCDOObject internalCDOObject : objectToRemove)
+ newObjects.remove(internalCDOObject);
+ }
+ }
+
+ protected boolean isSubscribe(InternalCDOObject eObject)
+ {
+ return (persistedObjects.get(eObject) != null);
+ }
+
+ private void subscribe(EObject eObject, Adapter adapter, int adjust)
+ {
+ synchronized (persistedObjects)
+ {
+ if (!getChangeSubscriptionPolicy().valid(eObject, adapter)) return;
+
+ subscribe(eObject, adjust);
+ }
+ }
+
+ private void subscribe(EObject eObject, int adjust)
+ {
+ synchronized (persistedObjects)
+ {
+
+ InternalCDOObject internalCDOObject = FSMUtil.adapt(eObject, CDOViewImpl.this);
+
+ if (internalCDOObject.cdoView() != CDOViewImpl.this)
+ {
+ throw new CDOException("Object " + internalCDOObject + " doesn`t belong to this view.");
+ }
+
+ boolean isValid = valid(internalCDOObject);
+
+ Map<InternalCDOObject, Integer> subscribersMap = isValid ? persistedObjects : newObjects;
+
+ Integer count = subscribersMap.get(internalCDOObject);
+
+ if (count == null)
+ {
+ // Cannot adjust negative value
+ if (adjust < 0) throw new IllegalStateException();
+
+ count = 0;
+
+ // Notification need to be enable to send correct value to the server
+ if (isValid && getChangeSubscriptionPolicy() != CDOChangeSubscriptionPolicy.NONE)
+ {
+ List<CDOID> cdoIDs = new ArrayList<CDOID>();
+ cdoIDs.add(internalCDOObject.cdoID());
+ request(cdoIDs, true, false);
+ }
+ }
+
+ count += adjust;
+
+ // Look if objects need to be unsubscribe
+ if (count <= 0)
+ {
+ subscribersMap.remove(internalCDOObject);
+
+ // Notification need to be enable to send correct value to the server
+ if (isValid && getChangeSubscriptionPolicy() != CDOChangeSubscriptionPolicy.NONE)
+ {
+ List<CDOID> cdoIDs = new ArrayList<CDOID>();
+ cdoIDs.add(internalCDOObject.cdoID());
+ request(cdoIDs, false, false);
+ }
+ }
+ else
+ {
+ subscribersMap.put(internalCDOObject, count);
+ }
+
+ }
+ }
+
+ public void subscribe(EObject eObject, Adapter adapter)
+ {
+ subscribe(eObject, adapter, 1);
+ }
+
+ public void unsubscribe(EObject eObject, Adapter adapter)
+ {
+ subscribe(eObject, adapter, -1);
+ }
+ }
+
+ public void subscribe(EObject eObject, Adapter adapter)
+ {
+ changeSubscriptionManager.subscribe(eObject, adapter);
+ }
+
+ public void unsubscribe(EObject eObject, Adapter adapter)
+ {
+ changeSubscriptionManager.unsubscribe(eObject, adapter);
+ }
+
protected ConcurrentMap<CDOID, InternalCDOObject> createObjectsMap()
{
return new ReferenceValueMap.Weak<CDOID, InternalCDOObject>();
@@ -172,6 +366,21 @@ public class CDOViewImpl extends org.eclipse.net4j.util.event.Notifier implement
this.invalidationNotificationsEnabled = invalidationNotificationsEnabled;
}
+ public CDOChangeSubscriptionPolicy getChangeSubscriptionPolicy()
+ {
+ return this.changeSubscriptionPolicy;
+ }
+
+ public void setChangeSubscriptionPolicy(CDOChangeSubscriptionPolicy notificationsEnabled)
+ {
+ if (this.changeSubscriptionPolicy != notificationsEnabled)
+ {
+ changeSubscriptionPolicy = notificationsEnabled;
+
+ changeSubscriptionManager.notifyChangeSubcriptionPolicy();
+ }
+ }
+
public int getLoadRevisionCollectionChunkSize()
{
return loadRevisionCollectionChunkSize;
@@ -325,6 +534,8 @@ public class CDOViewImpl extends org.eclipse.net4j.util.event.Notifier implement
public InternalCDOObject getObject(CDOID id, boolean loadOnDemand)
{
+ if (id == null || id.isNull()) return null;
+
synchronized (objects)
{
if (id.equals(lastLookupID))
@@ -635,6 +846,24 @@ public class CDOViewImpl extends org.eclipse.net4j.util.event.Notifier implement
}
}
+ public void notifyChangeSubcription(Collection<CDORevisionDelta> deltas)
+ {
+ if (deltas != null && getChangeSubscriptionPolicy() != CDOChangeSubscriptionPolicy.NONE)
+ {
+ CDONotificationBuilder builder = new CDONotificationBuilder(getSession().getPackageRegistry());
+
+ for (CDORevisionDelta delta : deltas)
+ {
+ InternalCDOObject object = objects.get(delta.getID());
+ if (object != null && object.eNotificationRequired() && changeSubscriptionManager.isSubscribe(object))
+ {
+ NotificationImpl notification = builder.buildNotification(object, delta);
+ if (notification != null) notification.dispatch();
+ }
+ }
+ }
+ }
+
public int reload(CDOObject... objects)
{
Collection<InternalCDOObject> internalObjects;
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/ChangeSubscriptionRequest.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/ChangeSubscriptionRequest.java
new file mode 100644
index 0000000000..ec44b509bf
--- /dev/null
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/ChangeSubscriptionRequest.java
@@ -0,0 +1,76 @@
+/***************************************************************************
+ * Copyright (c) 2004 - 2008 Eike Stepper, Germany.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Simon McDuff - initial API and implementation
+ * 230832: Make remote invalidation configurable
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
+ **************************************************************************/
+package org.eclipse.emf.internal.cdo.protocol;
+
+import org.eclipse.emf.cdo.common.CDOProtocolConstants;
+import org.eclipse.emf.cdo.common.id.CDOID;
+import org.eclipse.emf.cdo.common.id.CDOIDUtil;
+
+import org.eclipse.emf.internal.cdo.bundle.OM;
+
+import org.eclipse.net4j.channel.IChannel;
+import org.eclipse.net4j.util.io.ExtendedDataInputStream;
+import org.eclipse.net4j.util.io.ExtendedDataOutputStream;
+import org.eclipse.net4j.util.om.trace.ContextTracer;
+
+import java.io.IOException;
+import java.util.List;
+
+/**
+ * @author Simon McDuff
+ */
+public class ChangeSubscriptionRequest extends CDOClientRequest<Boolean>
+{
+ private static final ContextTracer PROTOCOL = new ContextTracer(OM.DEBUG_PROTOCOL, ChangeSubscriptionRequest.class);
+
+ private int viewID;
+
+ private List<CDOID> cdoIDs;
+
+ private boolean registered;
+
+ private boolean clear;
+
+ public ChangeSubscriptionRequest(IChannel channel, int viewID, List<CDOID> cdoIDs, boolean registered, boolean clear)
+ {
+ super(channel);
+ this.viewID = viewID;
+ this.cdoIDs = cdoIDs;
+ this.registered = registered;
+ this.clear = clear;
+ }
+
+ @Override
+ protected short getSignalID()
+ {
+ return CDOProtocolConstants.SIGNAL_CHANGE_SUBSCRIPTION;
+ }
+
+ @Override
+ protected void requesting(ExtendedDataOutputStream out) throws IOException
+ {
+ if (PROTOCOL.isEnabled()) PROTOCOL.trace("View " + viewID + " subscribing to " + cdoIDs.size());
+
+ out.writeInt(viewID);
+ out.writeBoolean(clear);
+ out.writeInt(registered ? cdoIDs.size() : -cdoIDs.size());
+ for (CDOID id : cdoIDs)
+ CDOIDUtil.write(out, id);
+ }
+
+ @Override
+ protected Boolean confirming(ExtendedDataInputStream in) throws IOException
+ {
+ return in.readBoolean();
+ }
+}
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/InvalidationIndication.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/InvalidationIndication.java
index a44290171d..391669d776 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/InvalidationIndication.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/InvalidationIndication.java
@@ -7,12 +7,16 @@
*
* Contributors:
* Eike Stepper - initial API and implementation
+ * Simon McDuff - 233490: Change Subscription
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=233490
**************************************************************************/
package org.eclipse.emf.internal.cdo.protocol;
import org.eclipse.emf.cdo.common.CDOProtocolConstants;
import org.eclipse.emf.cdo.common.id.CDOID;
import org.eclipse.emf.cdo.common.id.CDOIDUtil;
+import org.eclipse.emf.cdo.common.revision.delta.CDORevisionDelta;
+import org.eclipse.emf.cdo.internal.common.revision.delta.CDORevisionDeltaImpl;
import org.eclipse.emf.internal.cdo.CDOSessionImpl;
import org.eclipse.emf.internal.cdo.bundle.OM;
@@ -22,7 +26,9 @@ import org.eclipse.net4j.util.io.ExtendedDataInputStream;
import org.eclipse.net4j.util.om.trace.ContextTracer;
import java.io.IOException;
+import java.util.ArrayList;
import java.util.HashSet;
+import java.util.List;
import java.util.Set;
/**
@@ -64,8 +70,20 @@ public class InvalidationIndication extends Indication
CDOID dirtyOID = CDOIDUtil.read(in, session);
dirtyOIDs.add(dirtyOID);
}
-
- session.notifyInvalidation(timeStamp, dirtyOIDs, null);
+
+ size = in.readInt();
+ if (PROTOCOL.isEnabled())
+ {
+ PROTOCOL.format("Reading {0} Deltas", size);
+ }
+
+ List<CDORevisionDelta> deltas = new ArrayList<CDORevisionDelta>();
+ for (int i = 0; i < size; i++)
+ {
+ deltas.add(new CDORevisionDeltaImpl(in, getSession().getPackageManager()));
+ }
+
+ session.notifyCommit(timeStamp, dirtyOIDs, deltas, null);
}
protected CDOSessionImpl getSession()
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/OpenSessionRequest.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/OpenSessionRequest.java
index a980178055..c5c2157de4 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/OpenSessionRequest.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/OpenSessionRequest.java
@@ -7,6 +7,8 @@
*
* Contributors:
* Eike Stepper - initial API and implementation
+ * Simon McDuff - 230832: Make remote invalidation configurable
+ * https://bugs.eclipse.org/bugs/show_bug.cgi?id=230832
**************************************************************************/
package org.eclipse.emf.internal.cdo.protocol;
@@ -38,11 +40,15 @@ public class OpenSessionRequest extends RequestWithConfirmation<OpenSessionResul
private boolean legacySupportEnabled;
- public OpenSessionRequest(IChannel channel, String repositoryName, boolean legacySupportEnabled)
+ private boolean passiveUpdateEnabled;
+
+ public OpenSessionRequest(IChannel channel, String repositoryName, boolean legacySupportEnabled,
+ boolean passiveUpdateEnabled)
{
super(channel);
this.repositoryName = repositoryName;
this.legacySupportEnabled = legacySupportEnabled;
+ this.passiveUpdateEnabled = passiveUpdateEnabled;
}
@Override
@@ -65,6 +71,12 @@ public class OpenSessionRequest extends RequestWithConfirmation<OpenSessionResul
PROTOCOL.format("Writing legacySupportEnabled: {0}", legacySupportEnabled);
}
out.writeBoolean(legacySupportEnabled);
+
+ if (PROTOCOL.isEnabled())
+ {
+ PROTOCOL.format("Writing passiveUpdateEnabled: {0}", passiveUpdateEnabled);
+ }
+ out.writeBoolean(passiveUpdateEnabled);
}
@Override
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/PassiveUpdateRequest.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/PassiveUpdateRequest.java
index 4654883ff9..132d06f724 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/PassiveUpdateRequest.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/PassiveUpdateRequest.java
@@ -44,7 +44,7 @@ public class PassiveUpdateRequest extends SyncRevisionRequest
@Override
protected short getSignalID()
{
- return CDOProtocolConstants.SIGNAL_AUTOMATIC_REFRESH;
+ return CDOProtocolConstants.SIGNAL_PASSIVE_UPDATE;
}
@Override
diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/SyncRevisionRequest.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/SyncRevisionRequest.java
index f62aecd8b7..230991e7bc 100644
--- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/SyncRevisionRequest.java
+++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/protocol/SyncRevisionRequest.java
@@ -99,7 +99,7 @@ public class SyncRevisionRequest extends CDOClientRequest<Set<CDOID>>
if (PROTOCOL.isEnabled()) PROTOCOL.trace("Synchronization received " + size + " dirty objects");
- cdoSession.refresh(listofDirtyObjects);
+ cdoSession.notifySync(listofDirtyObjects);
return listofDirtyObjects;
}

Back to the top