diff --git a/spark/src/main/java/org/apache/zeppelin/spark/ZeppelinContext.java b/spark/src/main/java/org/apache/zeppelin/spark/ZeppelinContext.java index 6869161b1c4..926f3e7546b 100644 --- a/spark/src/main/java/org/apache/zeppelin/spark/ZeppelinContext.java +++ b/spark/src/main/java/org/apache/zeppelin/spark/ZeppelinContext.java @@ -427,7 +427,7 @@ public void run(List paragraphIdOrIdx) { /** * Run paragraphs - * @param paragraphIdOrIdxs list of paragraph id or idx + * @param paragraphIdOrIdx list of paragraph id or idx */ public void run(List paragraphIdOrIdx, InterpreterContext context) { for (Object idOrIdx : paragraphIdOrIdx) { @@ -475,17 +475,17 @@ private AngularObject getAngularObject(String name, InterpreterContext interpret AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); String noteId = interpreterContext.getNoteId(); // try get local object - AngularObject ao = registry.get(name, interpreterContext.getNoteId()); + AngularObject ao = registry.get(name, interpreterContext.getNoteId(), null); if (ao == null) { // then global object - ao = registry.get(name, null); + ao = registry.get(name, null, null); } return ao; } /** - * Get angular object. Look up local registry first and then global registry + * Get angular object. Look up notebook scope first and then global scope * @param name variable name * @return value */ @@ -499,13 +499,13 @@ public Object angular(String name) { } /** - * Get angular object. Look up global registry + * Get angular object. Look up global scope * @param name variable name * @return value */ public Object angularGlobal(String name) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - AngularObject ao = registry.get(name, null); + AngularObject ao = registry.get(name, null, null); if (ao == null) { return null; } else { @@ -514,7 +514,7 @@ public Object angularGlobal(String name) { } /** - * Create angular variable in local registry and bind with front end Angular display system. + * Create angular variable in notebook scope and bind with front end Angular display system. * If variable exists, it'll be overwritten. * @param name name of the variable * @param o value @@ -524,7 +524,7 @@ public void angularBind(String name, Object o) { } /** - * Create angular variable in global registry and bind with front end Angular display system. + * Create angular variable in global scope and bind with front end Angular display system. * If variable exists, it'll be overwritten. * @param name name of the variable * @param o value @@ -534,7 +534,7 @@ public void angularBindGlobal(String name, Object o) { } /** - * Create angular variable in local registry and bind with front end Angular display system. + * Create angular variable in local scope and bind with front end Angular display system. * If variable exists, value will be overwritten and watcher will be added. * @param name name of variable * @param o value @@ -545,7 +545,7 @@ public void angularBind(String name, Object o, AngularObjectWatcher watcher) { } /** - * Create angular variable in global registry and bind with front end Angular display system. + * Create angular variable in global scope and bind with front end Angular display system. * If variable exists, value will be overwritten and watcher will be added. * @param name name of variable * @param o value @@ -556,7 +556,7 @@ public void angularBindGlobal(String name, Object o, AngularObjectWatcher watche } /** - * Add watcher into angular variable (local registry) + * Add watcher into angular variable (local scope) * @param name name of the variable * @param watcher watcher */ @@ -565,7 +565,7 @@ public void angularWatch(String name, AngularObjectWatcher watcher) { } /** - * Add watcher into angular variable (global registry) + * Add watcher into angular variable (global scope) * @param name name of the variable * @param watcher watcher */ @@ -649,7 +649,7 @@ public void angularUnbindGlobal(String name) { } /** - * Create angular variable in local registry and bind with front end Angular display system. + * Create angular variable in notebook scope and bind with front end Angular display system. * If variable exists, it'll be overwritten. * @param name name of the variable * @param o value @@ -657,15 +657,16 @@ public void angularUnbindGlobal(String name) { private void angularBind(String name, Object o, String noteId) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - if (registry.get(name, noteId) == null) { - registry.add(name, o, noteId); + if (registry.get(name, noteId, null) == null) { + registry.add(name, o, noteId, null); } else { - registry.get(name, noteId).set(o); + registry.get(name, noteId, null).set(o); } } /** - * Create angular variable in local registry and bind with front end Angular display system. + * Create angular variable in notebook scope and bind with front end Angular display + * system. * If variable exists, value will be overwritten and watcher will be added. * @param name name of variable * @param o value @@ -674,10 +675,10 @@ private void angularBind(String name, Object o, String noteId) { private void angularBind(String name, Object o, String noteId, AngularObjectWatcher watcher) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - if (registry.get(name, noteId) == null) { - registry.add(name, o, noteId); + if (registry.get(name, noteId, null) == null) { + registry.add(name, o, noteId, null); } else { - registry.get(name, noteId).set(o); + registry.get(name, noteId, null).set(o); } angularWatch(name, watcher); } @@ -690,8 +691,8 @@ private void angularBind(String name, Object o, String noteId, AngularObjectWatc private void angularWatch(String name, String noteId, AngularObjectWatcher watcher) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - if (registry.get(name, noteId) != null) { - registry.get(name, noteId).addWatcher(watcher); + if (registry.get(name, noteId, null) != null) { + registry.get(name, noteId, null).addWatcher(watcher); } } @@ -729,8 +730,8 @@ public void watch(Object oldObject, Object newObject, */ private void angularUnwatch(String name, String noteId, AngularObjectWatcher watcher) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - if (registry.get(name, noteId) != null) { - registry.get(name, noteId).removeWatcher(watcher); + if (registry.get(name, noteId, null) != null) { + registry.get(name, noteId, null).removeWatcher(watcher); } } @@ -740,8 +741,8 @@ private void angularUnwatch(String name, String noteId, AngularObjectWatcher wat */ private void angularUnwatch(String name, String noteId) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - if (registry.get(name, noteId) != null) { - registry.get(name, noteId).clearAllWatchers(); + if (registry.get(name, noteId, null) != null) { + registry.get(name, noteId, null).clearAllWatchers(); } } @@ -751,6 +752,6 @@ private void angularUnwatch(String name, String noteId) { */ private void angularUnbind(String name, String noteId) { AngularObjectRegistry registry = interpreterContext.getAngularObjectRegistry(); - registry.remove(name, noteId); + registry.remove(name, noteId, null); } } diff --git a/testing/startSparkCluster.sh b/testing/startSparkCluster.sh index 7333ab09e07..8b7ad36deed 100755 --- a/testing/startSparkCluster.sh +++ b/testing/startSparkCluster.sh @@ -34,7 +34,7 @@ if [ ! -d "${SPARK_HOME}" ]; then echo "${SPARK_VERSION}" | grep "^1.[12].[0-9]" > /dev/null if [ $? -eq 0 ]; then # spark 1.1.x and spark 1.2.x can be downloaded from archive - wget http://archive.apache.org/dist/spark/spark-${SPARK_VERSION}/spark-${SPARK_VERSION}-bin-hadoop${HADOOP_VERSION}.tgz + wget -q http://archive.apache.org/dist/spark/spark-${SPARK_VERSION}/spark-${SPARK_VERSION}-bin-hadoop${HADOOP_VERSION}.tgz else # spark 1.3.x and later can be downloaded from mirror # get download address from mirror @@ -42,7 +42,7 @@ if [ ! -d "${SPARK_HOME}" ]; then PREFFERED=$(echo "${MIRROR_INFO}" | grep preferred | sed 's/[^"]*.preferred.: .\([^"]*\).*/\1/g') PATHINFO=$(echo "${MIRROR_INFO}" | grep path_info | sed 's/[^"]*.path_info.: .\([^"]*\).*/\1/g') - wget "${PREFFERED}${PATHINFO}" + wget -q "${PREFFERED}${PATHINFO}" fi tar zxf spark-${SPARK_VERSION}-bin-hadoop${HADOOP_VERSION}.tgz fi diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObject.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObject.java index cebe4cc4911..4b0c3e93d75 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObject.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObject.java @@ -26,7 +26,9 @@ import org.slf4j.LoggerFactory; /** - * + * AngularObject provides binding between back-end (interpreter) and front-end + * User provided object will automatically synchronized with front-end side. + * i.e. update from back-end will be sent to front-end, update from front-end will sent-to backend * * @param */ @@ -39,27 +41,70 @@ public class AngularObject { = new LinkedList(); private String noteId; // noteId belonging to. null for global scope - - protected AngularObject(String name, T o, String noteId, + private String paragraphId; // paragraphId belongs to. null for notebook scope + + /** + * To create new AngularObject, use AngularObjectRegistry.add() + * + * @param name name of object + * @param o reference to user provided object to sent to front-end + * @param noteId noteId belongs to. can be null + * @param paragraphId paragraphId belongs to. can be null + * @param listener event listener + */ + protected AngularObject(String name, T o, String noteId, String paragraphId, AngularObjectListener listener) { this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; this.listener = listener; object = o; } + /** + * Get name of this object + * @return name + */ public String getName() { return name; } - + + /** + * Set noteId + * @param noteId noteId belongs to. can be null + */ public void setNoteId(String noteId) { this.noteId = noteId; } - + + /** + * Get noteId + * @return noteId + */ public String getNoteId() { return noteId; } - + + /** + * get ParagraphId + * @return paragraphId + */ + public String getParagraphId() { + return paragraphId; + } + + /** + * Set paragraphId + * @param paragraphId paragraphId. can be null + */ + public void setParagraphId(String paragraphId) { + this.paragraphId = paragraphId; + } + + /** + * Check if it is global scope object + * @return true it is global scope + */ public boolean isGlobal() { return noteId == null; } @@ -70,26 +115,47 @@ public boolean equals(Object o) { AngularObject ao = (AngularObject) o; if (noteId == null && ao.noteId == null || (noteId != null && ao.noteId != null && noteId.equals(ao.noteId))) { - return name.equals(ao.name); + if (paragraphId == null && ao.paragraphId == null || + (paragraphId != null && ao.paragraphId != null && paragraphId.equals(ao.paragraphId))) { + return name.equals(ao.name); + } } } return false; } + /** + * Get value + * @return + */ public Object get() { return object; } + /** + * fire updated() event for listener + * Note that it does not invoke watcher.watch() + */ public void emit(){ if (listener != null) { listener.updated(this); } } - + + /** + * Set value + * @param o reference to new user provided object + */ public void set(T o) { set(o, true); } + /** + * Set value + * @param o reference to new user provided object + * @param emit false on skip firing event for listener. note that it does not skip invoke + * watcher.watch() in any case + */ public void set(T o, boolean emit) { final T before = object; final T after = o; @@ -119,26 +185,47 @@ public void run() { } } + /** + * Set event listener for this object + * @param listener + */ public void setListener(AngularObjectListener listener) { this.listener = listener; } + /** + * Get event listener of this object + * @return event listener + */ public AngularObjectListener getListener() { return listener; } + /** + * Add a watcher for this object. + * Multiple watcher can be registered. + * + * @param watcher watcher to add + */ public void addWatcher(AngularObjectWatcher watcher) { synchronized (watchers) { watchers.add(watcher); } } + /** + * Remove a watcher from this object + * @param watcher watcher to remove + */ public void removeWatcher(AngularObjectWatcher watcher) { synchronized (watchers) { watchers.remove(watcher); } } + /** + * Remove all watchers from this object + */ public void clearAllWatchers() { synchronized (watchers) { watchers.clear(); diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistry.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistry.java index d6bab7b732c..cf360af124b 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistry.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistry.java @@ -26,9 +26,10 @@ /** * AngularObjectRegistry keeps all the object that binded to Angular Display System. * AngularObjectRegistry is created per interpreter group. - * It keeps two different set of AngularObjects : - * - globalRegistry: Shared to all notebook that uses the same interpreter group - * - localRegistry: AngularObject is valid only inside of a single notebook + * It provides three different scope of AngularObjects : + * - Paragraphscope : AngularObject is valid in specific paragraph + * - Notebook scope: AngularObject is valid in a single notebook + * - Global scope : Shared to all notebook that uses the same interpreter group */ public class AngularObjectRegistry { Map> registry = @@ -60,26 +61,36 @@ public AngularObjectRegistryListener getListener() { /** * Add object into registry - * @param name - * @param o - * @param noteId noteId belonging to. null for global object. - * @return + * + * Paragraph scope when noteId and paragraphId both not null + * Notebook scope when paragraphId is null + * Global scope when noteId and paragraphId both null + * + * @param name Name of object + * @param o Reference to the object + * @param noteId noteId belonging to. null for global scope + * @param paragraphId paragraphId belongs to. null for notebook scope + * @return AngularObject that added */ - public AngularObject add(String name, Object o, String noteId) { - return add(name, o, noteId, true); + public AngularObject add(String name, Object o, String noteId, String paragraphId) { + return add(name, o, noteId, paragraphId, true); } - private String getRegistryKey(String noteId) { + private String getRegistryKey(String noteId, String paragraphId) { if (noteId == null) { return GLOBAL_KEY; } else { - return noteId; + if (paragraphId == null) { + return noteId; + } else { + return noteId + "_" + paragraphId; + } } } - private Map getRegistryForKey(String noteId) { + private Map getRegistryForKey(String noteId, String paragraphId) { synchronized (registry) { - String key = getRegistryKey(noteId); + String key = getRegistryKey(noteId, paragraphId); if (!registry.containsKey(key)) { registry.put(key, new HashMap()); } @@ -87,12 +98,27 @@ private Map getRegistryForKey(String noteId) { return registry.get(key); } } - - public AngularObject add(String name, Object o, String noteId, boolean emit) { - AngularObject ao = createNewAngularObject(name, o, noteId); + + /** + * Add object into registry + * + * Paragraph scope when noteId and paragraphId both not null + * Notebook scope when paragraphId is null + * Global scope when noteId and paragraphId both null + * + * @param name Name of object + * @param o Reference to the object + * @param noteId noteId belonging to. null for global scope + * @param paragraphId paragraphId belongs to. null for notebook scope + * @param emit skip firing onAdd event on false + * @return AngularObject that added + */ + public AngularObject add(String name, Object o, String noteId, String paragraphId, + boolean emit) { + AngularObject ao = createNewAngularObject(name, o, noteId, paragraphId); synchronized (registry) { - Map noteLocalRegistry = getRegistryForKey(noteId); + Map noteLocalRegistry = getRegistryForKey(noteId, paragraphId); noteLocalRegistry.put(name, ao); if (listener != null && emit) { listener.onAdd(interpreterId, ao); @@ -102,49 +128,90 @@ public AngularObject add(String name, Object o, String noteId, boolean emit) { return ao; } - protected AngularObject createNewAngularObject(String name, Object o, String noteId) { - return new AngularObject(name, o, noteId, angularObjectListener); + protected AngularObject createNewAngularObject(String name, Object o, String noteId, + String paragraphId) { + return new AngularObject(name, o, noteId, paragraphId, angularObjectListener); } protected AngularObjectListener getAngularObjectListener() { return angularObjectListener; } - public AngularObject remove(String name, String noteId) { - return remove(name, noteId, true); + /** + * Remove a object from registry + * + * @param name Name of object to remove + * @param noteId noteId belongs to. null for global scope + * @param paragraphId paragraphId belongs to. null for notebook scope + * @return removed object. null if object is not found in registry + */ + public AngularObject remove(String name, String noteId, String paragraphId) { + return remove(name, noteId, paragraphId, true); } - public AngularObject remove(String name, String noteId, boolean emit) { + /** + * Remove a object from registry + * + * @param name Name of object to remove + * @param noteId noteId belongs to. null for global scope + * @param paragraphId paragraphId belongs to. null for notebook scope + * @param emit skip fireing onRemove event on false + * @return removed object. null if object is not found in registry + */ + public AngularObject remove(String name, String noteId, String paragraphId, boolean emit) { synchronized (registry) { - Map r = getRegistryForKey(noteId); + Map r = getRegistryForKey(noteId, paragraphId); AngularObject o = r.remove(name); if (listener != null && emit) { - listener.onRemove(interpreterId, name, noteId);; + listener.onRemove(interpreterId, name, noteId, paragraphId);; } return o; } } - public void removeAll(String noteId) { + /** + * Remove all angular object in the scope. + * + * Remove all paragraph scope angular object when noteId and paragraphId both not null + * Remove all notebook scope angular object when paragraphId is null + * Remove all global scope angular objects when noteId and paragraphId both null + * + * @param noteId noteId + * @param paragraphId paragraphId + */ + public void removeAll(String noteId, String paragraphId) { synchronized (registry) { - List all = getAll(noteId); + List all = getAll(noteId, paragraphId); for (AngularObject ao : all) { - remove(ao.getName(), noteId); + remove(ao.getName(), noteId, paragraphId); } } } - public AngularObject get(String name, String noteId) { + /** + * Get a object from registry + * @param name name of object + * @param noteId noteId that belongs to + * @param paragraphId paragraphId that belongs to + * @return angularobject. null when not found + */ + public AngularObject get(String name, String noteId, String paragraphId) { synchronized (registry) { - Map r = getRegistryForKey(noteId); + Map r = getRegistryForKey(noteId, paragraphId); return r.get(name); } } - public List getAll(String noteId) { + /** + * Get all object in the scope + * @param noteId noteId that belongs to + * @param paragraphId paragraphId that belongs to + * @return all angularobject in the scope + */ + public List getAll(String noteId, String paragraphId) { List all = new LinkedList(); synchronized (registry) { - Map r = getRegistryForKey(noteId); + Map r = getRegistryForKey(noteId, paragraphId); if (r != null) { all.addAll(r.values()); } @@ -153,20 +220,24 @@ public List getAll(String noteId) { } /** - * Get all object with global merged + * Get all angular object related to specific note. + * That includes all global scope objects, notebook scope objects and paragraph scope objects + * belongs to the noteId. + * * @param noteId * @return */ public List getAllWithGlobal(String noteId) { List all = new LinkedList(); synchronized (registry) { - Map global = getRegistryForKey(null); + Map global = getRegistryForKey(null, null); if (global != null) { all.addAll(global.values()); } - Map local = getRegistryForKey(noteId); - if (local != null) { - all.addAll(local.values()); + for (String key : registry.keySet()) { + if (key.startsWith(noteId)) { + all.addAll(registry.get(key).values()); + } } } return all; diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistryListener.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistryListener.java index 3ba57d7b1af..103336dbfaa 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistryListener.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/display/AngularObjectRegistryListener.java @@ -24,5 +24,5 @@ public interface AngularObjectRegistryListener { public void onAdd(String interpreterGroupId, AngularObject object); public void onUpdate(String interpreterGroupId, AngularObject object); - public void onRemove(String interpreterGroupId, String name, String noteId); + public void onRemove(String interpreterGroupId, String name, String noteId, String paragraphId); } diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObject.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObject.java index 351a2bb1b4a..8948b4ed3e2 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObject.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObject.java @@ -21,16 +21,17 @@ import org.apache.zeppelin.display.AngularObjectListener; /** - * + * Proxy for AngularObject that exists in remote interpreter process */ public class RemoteAngularObject extends AngularObject { private transient RemoteInterpreterProcess remoteInterpreterProcess; - RemoteAngularObject(String name, Object o, String noteId, String interpreterGroupId, + RemoteAngularObject(String name, Object o, String noteId, String paragraphId, String + interpreterGroupId, AngularObjectListener listener, RemoteInterpreterProcess remoteInterpreterProcess) { - super(name, o, noteId, listener); + super(name, o, noteId, paragraphId, listener); this.remoteInterpreterProcess = remoteInterpreterProcess; } @@ -44,7 +45,8 @@ public void set(Object o, boolean emitWeb, boolean emitRemoteProcess) { if (emitRemoteProcess) { // send updated value to remote interpreter - remoteInterpreterProcess.updateRemoteAngularObject(getName(), getNoteId(), o); + remoteInterpreterProcess.updateRemoteAngularObject(getName(), getNoteId(), getParagraphId() + , o); } } } diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectRegistry.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectRegistry.java index 9b33cb814d1..790ed950bb8 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectRegistry.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectRegistry.java @@ -33,7 +33,7 @@ import com.google.gson.Gson; /** - * + * Proxy for AngularObjectRegistry that exists in remote interpreter process */ public class RemoteAngularObjectRegistry extends AngularObjectRegistry { Logger logger = LoggerFactory.getLogger(RemoteAngularObjectRegistry.class); @@ -70,7 +70,8 @@ private RemoteInterpreterProcess getRemoteInterpreterProcess() { * @param noteId * @return */ - public AngularObject addAndNotifyRemoteProcess(String name, Object o, String noteId) { + public AngularObject addAndNotifyRemoteProcess(String name, Object o, String noteId, String + paragraphId) { Gson gson = new Gson(); RemoteInterpreterProcess remoteInterpreterProcess = getRemoteInterpreterProcess(); if (!remoteInterpreterProcess.isRunning()) { @@ -81,8 +82,8 @@ public AngularObject addAndNotifyRemoteProcess(String name, Object o, String not boolean broken = false; try { client = remoteInterpreterProcess.getClient(); - client.angularObjectAdd(name, noteId, gson.toJson(o)); - return super.add(name, o, noteId, true); + client.angularObjectAdd(name, noteId, paragraphId, gson.toJson(o)); + return super.add(name, o, noteId, paragraphId, true); } catch (TException e) { broken = true; logger.error("Error", e); @@ -101,9 +102,11 @@ public AngularObject addAndNotifyRemoteProcess(String name, Object o, String not * this method should be used instead of remove() * @param name * @param noteId + * @param paragraphId * @return */ - public AngularObject removeAndNotifyRemoteProcess(String name, String noteId) { + public AngularObject removeAndNotifyRemoteProcess(String name, String noteId, String + paragraphId) { RemoteInterpreterProcess remoteInterpreterProcess = getRemoteInterpreterProcess(); if (!remoteInterpreterProcess.isRunning()) { return null; @@ -113,8 +116,8 @@ public AngularObject removeAndNotifyRemoteProcess(String name, String noteId) { boolean broken = false; try { client = remoteInterpreterProcess.getClient(); - client.angularObjectRemove(name, noteId); - return super.remove(name, noteId); + client.angularObjectRemove(name, noteId, paragraphId); + return super.remove(name, noteId, paragraphId); } catch (TException e) { broken = true; logger.error("Error", e); @@ -128,20 +131,21 @@ public AngularObject removeAndNotifyRemoteProcess(String name, String noteId) { return null; } - public void removeAllAndNotifyRemoteProcess(String noteId) { - List all = getAll(noteId); + public void removeAllAndNotifyRemoteProcess(String noteId, String paragraphId) { + List all = getAll(noteId, paragraphId); for (AngularObject ao : all) { - removeAndNotifyRemoteProcess(ao.getName(), noteId); + removeAndNotifyRemoteProcess(ao.getName(), noteId, paragraphId); } } @Override - protected AngularObject createNewAngularObject(String name, Object o, String noteId) { + protected AngularObject createNewAngularObject(String name, Object o, String noteId, String + paragraphId) { RemoteInterpreterProcess remoteInterpreterProcess = getRemoteInterpreterProcess(); if (remoteInterpreterProcess == null) { throw new RuntimeException("Remote Interpreter process not found"); } - return new RemoteAngularObject(name, o, noteId, getInterpreterGroupId(), + return new RemoteAngularObject(name, o, noteId, paragraphId, getInterpreterGroupId(), getAngularObjectListener(), getRemoteInterpreterProcess()); } diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterEventPoller.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterEventPoller.java index 61862053fce..b1055e21bd0 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterEventPoller.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterEventPoller.java @@ -94,12 +94,12 @@ public void run() { } else if (event.getType() == RemoteInterpreterEventType.ANGULAR_OBJECT_ADD) { AngularObject angularObject = gson.fromJson(event.getData(), AngularObject.class); angularObjectRegistry.add(angularObject.getName(), - angularObject.get(), angularObject.getNoteId()); + angularObject.get(), angularObject.getNoteId(), angularObject.getParagraphId()); } else if (event.getType() == RemoteInterpreterEventType.ANGULAR_OBJECT_UPDATE) { AngularObject angularObject = gson.fromJson(event.getData(), AngularObject.class); AngularObject localAngularObject = angularObjectRegistry.get( - angularObject.getName(), angularObject.getNoteId()); + angularObject.getName(), angularObject.getNoteId(), angularObject.getParagraphId()); if (localAngularObject instanceof RemoteAngularObject) { // to avoid ping-pong loop ((RemoteAngularObject) localAngularObject).set( @@ -109,7 +109,8 @@ public void run() { } } else if (event.getType() == RemoteInterpreterEventType.ANGULAR_OBJECT_REMOVE) { AngularObject angularObject = gson.fromJson(event.getData(), AngularObject.class); - angularObjectRegistry.remove(angularObject.getName(), angularObject.getNoteId()); + angularObjectRegistry.remove(angularObject.getName(), angularObject.getNoteId(), + angularObject.getParagraphId()); } else if (event.getType() == RemoteInterpreterEventType.RUN_INTERPRETER_CONTEXT_RUNNER) { InterpreterContextRunner runnerFromRemote = gson.fromJson( event.getData(), RemoteInterpreterContextRunner.class); diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterProcess.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterProcess.java index 56b54850c7a..5612a2bcf10 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterProcess.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterProcess.java @@ -267,7 +267,7 @@ public int getNumIdleClient() { * @param name * @param o */ - public void updateRemoteAngularObject(String name, String noteId, Object o) { + public void updateRemoteAngularObject(String name, String noteId, String paragraphId, Object o) { Client client = null; try { client = getClient(); @@ -283,7 +283,7 @@ public void updateRemoteAngularObject(String name, String noteId, Object o) { boolean broken = false; try { Gson gson = new Gson(); - client.angularObjectUpdate(name, noteId, gson.toJson(o)); + client.angularObjectUpdate(name, noteId, paragraphId, gson.toJson(o)); } catch (TException e) { broken = true; logger.error("Can't update angular object", e); diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterServer.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterServer.java index 728d2108cf4..a59293b483b 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterServer.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/remote/RemoteInterpreterServer.java @@ -480,7 +480,7 @@ public void onUpdate(String interpreterGroupId, AngularObject object) { } @Override - public void onRemove(String interpreterGroupId, String name, String noteId) { + public void onRemove(String interpreterGroupId, String name, String noteId, String paragraphId) { Map removeObject = new HashMap(); removeObject.put("name", name); removeObject.put("noteId", noteId); @@ -519,15 +519,16 @@ public RemoteInterpreterEvent getEvent() throws TException { * called when object is updated in client (web) side. * @param name * @param noteId noteId where the update issues + * @param paragraphId paragraphId where the update issues * @param object * @throws TException */ @Override - public void angularObjectUpdate(String name, String noteId, String object) + public void angularObjectUpdate(String name, String noteId, String paragraphId, String object) throws TException { AngularObjectRegistry registry = interpreterGroup.getAngularObjectRegistry(); // first try local objects - AngularObject ao = registry.get(name, noteId); + AngularObject ao = registry.get(name, noteId, paragraphId); if (ao == null) { logger.error("Angular object {} not exists", name); return; @@ -576,13 +577,13 @@ public void angularObjectUpdate(String name, String noteId, String object) * Dont't need to emit event to zeppelin server */ @Override - public void angularObjectAdd(String name, String noteId, String object) + public void angularObjectAdd(String name, String noteId, String paragraphId, String object) throws TException { AngularObjectRegistry registry = interpreterGroup.getAngularObjectRegistry(); // first try local objects - AngularObject ao = registry.get(name, noteId); + AngularObject ao = registry.get(name, noteId, paragraphId); if (ao != null) { - angularObjectUpdate(name, noteId, object); + angularObjectUpdate(name, noteId, paragraphId, object); return; } @@ -602,12 +603,13 @@ public void angularObjectAdd(String name, String noteId, String object) value = gson.fromJson(object, String.class); } - registry.add(name, value, noteId, false); + registry.add(name, value, noteId, paragraphId, false); } @Override - public void angularObjectRemove(String name, String noteId) throws TException { + public void angularObjectRemove(String name, String noteId, String paragraphId) throws + TException { AngularObjectRegistry registry = interpreterGroup.getAngularObjectRegistry(); - registry.remove(name, noteId, false); + registry.remove(name, noteId, paragraphId, false); } } diff --git a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/thrift/RemoteInterpreterService.java b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/thrift/RemoteInterpreterService.java index 738b453d0e2..fbcc5140dbd 100644 --- a/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/thrift/RemoteInterpreterService.java +++ b/zeppelin-interpreter/src/main/java/org/apache/zeppelin/interpreter/thrift/RemoteInterpreterService.java @@ -78,11 +78,11 @@ public interface Iface { public RemoteInterpreterEvent getEvent() throws org.apache.thrift.TException; - public void angularObjectUpdate(String name, String noteId, String object) throws org.apache.thrift.TException; + public void angularObjectUpdate(String name, String noteId, String paragraphId, String object) throws org.apache.thrift.TException; - public void angularObjectAdd(String name, String noteId, String object) throws org.apache.thrift.TException; + public void angularObjectAdd(String name, String noteId, String paragraphId, String object) throws org.apache.thrift.TException; - public void angularObjectRemove(String name, String noteId) throws org.apache.thrift.TException; + public void angularObjectRemove(String name, String noteId, String paragraphId) throws org.apache.thrift.TException; } @@ -110,11 +110,11 @@ public interface AsyncIface { public void getEvent(org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; - public void angularObjectUpdate(String name, String noteId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; + public void angularObjectUpdate(String name, String noteId, String paragraphId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; - public void angularObjectAdd(String name, String noteId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; + public void angularObjectAdd(String name, String noteId, String paragraphId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; - public void angularObjectRemove(String name, String noteId, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; + public void angularObjectRemove(String name, String noteId, String paragraphId, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException; } @@ -381,17 +381,18 @@ public RemoteInterpreterEvent recv_getEvent() throws org.apache.thrift.TExceptio throw new org.apache.thrift.TApplicationException(org.apache.thrift.TApplicationException.MISSING_RESULT, "getEvent failed: unknown result"); } - public void angularObjectUpdate(String name, String noteId, String object) throws org.apache.thrift.TException + public void angularObjectUpdate(String name, String noteId, String paragraphId, String object) throws org.apache.thrift.TException { - send_angularObjectUpdate(name, noteId, object); + send_angularObjectUpdate(name, noteId, paragraphId, object); recv_angularObjectUpdate(); } - public void send_angularObjectUpdate(String name, String noteId, String object) throws org.apache.thrift.TException + public void send_angularObjectUpdate(String name, String noteId, String paragraphId, String object) throws org.apache.thrift.TException { angularObjectUpdate_args args = new angularObjectUpdate_args(); args.setName(name); args.setNoteId(noteId); + args.setParagraphId(paragraphId); args.setObject(object); sendBase("angularObjectUpdate", args); } @@ -403,17 +404,18 @@ public void recv_angularObjectUpdate() throws org.apache.thrift.TException return; } - public void angularObjectAdd(String name, String noteId, String object) throws org.apache.thrift.TException + public void angularObjectAdd(String name, String noteId, String paragraphId, String object) throws org.apache.thrift.TException { - send_angularObjectAdd(name, noteId, object); + send_angularObjectAdd(name, noteId, paragraphId, object); recv_angularObjectAdd(); } - public void send_angularObjectAdd(String name, String noteId, String object) throws org.apache.thrift.TException + public void send_angularObjectAdd(String name, String noteId, String paragraphId, String object) throws org.apache.thrift.TException { angularObjectAdd_args args = new angularObjectAdd_args(); args.setName(name); args.setNoteId(noteId); + args.setParagraphId(paragraphId); args.setObject(object); sendBase("angularObjectAdd", args); } @@ -425,17 +427,18 @@ public void recv_angularObjectAdd() throws org.apache.thrift.TException return; } - public void angularObjectRemove(String name, String noteId) throws org.apache.thrift.TException + public void angularObjectRemove(String name, String noteId, String paragraphId) throws org.apache.thrift.TException { - send_angularObjectRemove(name, noteId); + send_angularObjectRemove(name, noteId, paragraphId); recv_angularObjectRemove(); } - public void send_angularObjectRemove(String name, String noteId) throws org.apache.thrift.TException + public void send_angularObjectRemove(String name, String noteId, String paragraphId) throws org.apache.thrift.TException { angularObjectRemove_args args = new angularObjectRemove_args(); args.setName(name); args.setNoteId(noteId); + args.setParagraphId(paragraphId); sendBase("angularObjectRemove", args); } @@ -831,9 +834,9 @@ public RemoteInterpreterEvent getResult() throws org.apache.thrift.TException { } } - public void angularObjectUpdate(String name, String noteId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException { + public void angularObjectUpdate(String name, String noteId, String paragraphId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException { checkReady(); - angularObjectUpdate_call method_call = new angularObjectUpdate_call(name, noteId, object, resultHandler, this, ___protocolFactory, ___transport); + angularObjectUpdate_call method_call = new angularObjectUpdate_call(name, noteId, paragraphId, object, resultHandler, this, ___protocolFactory, ___transport); this.___currentMethod = method_call; ___manager.call(method_call); } @@ -841,11 +844,13 @@ public void angularObjectUpdate(String name, String noteId, String object, org.a public static class angularObjectUpdate_call extends org.apache.thrift.async.TAsyncMethodCall { private String name; private String noteId; + private String paragraphId; private String object; - public angularObjectUpdate_call(String name, String noteId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler, org.apache.thrift.async.TAsyncClient client, org.apache.thrift.protocol.TProtocolFactory protocolFactory, org.apache.thrift.transport.TNonblockingTransport transport) throws org.apache.thrift.TException { + public angularObjectUpdate_call(String name, String noteId, String paragraphId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler, org.apache.thrift.async.TAsyncClient client, org.apache.thrift.protocol.TProtocolFactory protocolFactory, org.apache.thrift.transport.TNonblockingTransport transport) throws org.apache.thrift.TException { super(client, protocolFactory, transport, resultHandler, false); this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; this.object = object; } @@ -854,6 +859,7 @@ public void write_args(org.apache.thrift.protocol.TProtocol prot) throws org.apa angularObjectUpdate_args args = new angularObjectUpdate_args(); args.setName(name); args.setNoteId(noteId); + args.setParagraphId(paragraphId); args.setObject(object); args.write(prot); prot.writeMessageEnd(); @@ -869,9 +875,9 @@ public void getResult() throws org.apache.thrift.TException { } } - public void angularObjectAdd(String name, String noteId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException { + public void angularObjectAdd(String name, String noteId, String paragraphId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException { checkReady(); - angularObjectAdd_call method_call = new angularObjectAdd_call(name, noteId, object, resultHandler, this, ___protocolFactory, ___transport); + angularObjectAdd_call method_call = new angularObjectAdd_call(name, noteId, paragraphId, object, resultHandler, this, ___protocolFactory, ___transport); this.___currentMethod = method_call; ___manager.call(method_call); } @@ -879,11 +885,13 @@ public void angularObjectAdd(String name, String noteId, String object, org.apac public static class angularObjectAdd_call extends org.apache.thrift.async.TAsyncMethodCall { private String name; private String noteId; + private String paragraphId; private String object; - public angularObjectAdd_call(String name, String noteId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler, org.apache.thrift.async.TAsyncClient client, org.apache.thrift.protocol.TProtocolFactory protocolFactory, org.apache.thrift.transport.TNonblockingTransport transport) throws org.apache.thrift.TException { + public angularObjectAdd_call(String name, String noteId, String paragraphId, String object, org.apache.thrift.async.AsyncMethodCallback resultHandler, org.apache.thrift.async.TAsyncClient client, org.apache.thrift.protocol.TProtocolFactory protocolFactory, org.apache.thrift.transport.TNonblockingTransport transport) throws org.apache.thrift.TException { super(client, protocolFactory, transport, resultHandler, false); this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; this.object = object; } @@ -892,6 +900,7 @@ public void write_args(org.apache.thrift.protocol.TProtocol prot) throws org.apa angularObjectAdd_args args = new angularObjectAdd_args(); args.setName(name); args.setNoteId(noteId); + args.setParagraphId(paragraphId); args.setObject(object); args.write(prot); prot.writeMessageEnd(); @@ -907,9 +916,9 @@ public void getResult() throws org.apache.thrift.TException { } } - public void angularObjectRemove(String name, String noteId, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException { + public void angularObjectRemove(String name, String noteId, String paragraphId, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws org.apache.thrift.TException { checkReady(); - angularObjectRemove_call method_call = new angularObjectRemove_call(name, noteId, resultHandler, this, ___protocolFactory, ___transport); + angularObjectRemove_call method_call = new angularObjectRemove_call(name, noteId, paragraphId, resultHandler, this, ___protocolFactory, ___transport); this.___currentMethod = method_call; ___manager.call(method_call); } @@ -917,10 +926,12 @@ public void angularObjectRemove(String name, String noteId, org.apache.thrift.as public static class angularObjectRemove_call extends org.apache.thrift.async.TAsyncMethodCall { private String name; private String noteId; - public angularObjectRemove_call(String name, String noteId, org.apache.thrift.async.AsyncMethodCallback resultHandler, org.apache.thrift.async.TAsyncClient client, org.apache.thrift.protocol.TProtocolFactory protocolFactory, org.apache.thrift.transport.TNonblockingTransport transport) throws org.apache.thrift.TException { + private String paragraphId; + public angularObjectRemove_call(String name, String noteId, String paragraphId, org.apache.thrift.async.AsyncMethodCallback resultHandler, org.apache.thrift.async.TAsyncClient client, org.apache.thrift.protocol.TProtocolFactory protocolFactory, org.apache.thrift.transport.TNonblockingTransport transport) throws org.apache.thrift.TException { super(client, protocolFactory, transport, resultHandler, false); this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; } public void write_args(org.apache.thrift.protocol.TProtocol prot) throws org.apache.thrift.TException { @@ -928,6 +939,7 @@ public void write_args(org.apache.thrift.protocol.TProtocol prot) throws org.apa angularObjectRemove_args args = new angularObjectRemove_args(); args.setName(name); args.setNoteId(noteId); + args.setParagraphId(paragraphId); args.write(prot); prot.writeMessageEnd(); } @@ -1208,7 +1220,7 @@ protected boolean isOneway() { public angularObjectUpdate_result getResult(I iface, angularObjectUpdate_args args) throws org.apache.thrift.TException { angularObjectUpdate_result result = new angularObjectUpdate_result(); - iface.angularObjectUpdate(args.name, args.noteId, args.object); + iface.angularObjectUpdate(args.name, args.noteId, args.paragraphId, args.object); return result; } } @@ -1228,7 +1240,7 @@ protected boolean isOneway() { public angularObjectAdd_result getResult(I iface, angularObjectAdd_args args) throws org.apache.thrift.TException { angularObjectAdd_result result = new angularObjectAdd_result(); - iface.angularObjectAdd(args.name, args.noteId, args.object); + iface.angularObjectAdd(args.name, args.noteId, args.paragraphId, args.object); return result; } } @@ -1248,7 +1260,7 @@ protected boolean isOneway() { public angularObjectRemove_result getResult(I iface, angularObjectRemove_args args) throws org.apache.thrift.TException { angularObjectRemove_result result = new angularObjectRemove_result(); - iface.angularObjectRemove(args.name, args.noteId); + iface.angularObjectRemove(args.name, args.noteId, args.paragraphId); return result; } } @@ -1886,7 +1898,7 @@ protected boolean isOneway() { } public void start(I iface, angularObjectUpdate_args args, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws TException { - iface.angularObjectUpdate(args.name, args.noteId, args.object,resultHandler); + iface.angularObjectUpdate(args.name, args.noteId, args.paragraphId, args.object,resultHandler); } } @@ -1936,7 +1948,7 @@ protected boolean isOneway() { } public void start(I iface, angularObjectAdd_args args, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws TException { - iface.angularObjectAdd(args.name, args.noteId, args.object,resultHandler); + iface.angularObjectAdd(args.name, args.noteId, args.paragraphId, args.object,resultHandler); } } @@ -1986,7 +1998,7 @@ protected boolean isOneway() { } public void start(I iface, angularObjectRemove_args args, org.apache.thrift.async.AsyncMethodCallback resultHandler) throws TException { - iface.angularObjectRemove(args.name, args.noteId,resultHandler); + iface.angularObjectRemove(args.name, args.noteId, args.paragraphId,resultHandler); } } @@ -10007,7 +10019,8 @@ public static class angularObjectUpdate_args implements org.apache.thrift.TBase< private static final org.apache.thrift.protocol.TField NAME_FIELD_DESC = new org.apache.thrift.protocol.TField("name", org.apache.thrift.protocol.TType.STRING, (short)1); private static final org.apache.thrift.protocol.TField NOTE_ID_FIELD_DESC = new org.apache.thrift.protocol.TField("noteId", org.apache.thrift.protocol.TType.STRING, (short)2); - private static final org.apache.thrift.protocol.TField OBJECT_FIELD_DESC = new org.apache.thrift.protocol.TField("object", org.apache.thrift.protocol.TType.STRING, (short)3); + private static final org.apache.thrift.protocol.TField PARAGRAPH_ID_FIELD_DESC = new org.apache.thrift.protocol.TField("paragraphId", org.apache.thrift.protocol.TType.STRING, (short)3); + private static final org.apache.thrift.protocol.TField OBJECT_FIELD_DESC = new org.apache.thrift.protocol.TField("object", org.apache.thrift.protocol.TType.STRING, (short)4); private static final Map, SchemeFactory> schemes = new HashMap, SchemeFactory>(); static { @@ -10017,13 +10030,15 @@ public static class angularObjectUpdate_args implements org.apache.thrift.TBase< public String name; // required public String noteId; // required + public String paragraphId; // required public String object; // required /** The set of fields this struct contains, along with convenience methods for finding and manipulating them. */ public enum _Fields implements org.apache.thrift.TFieldIdEnum { NAME((short)1, "name"), NOTE_ID((short)2, "noteId"), - OBJECT((short)3, "object"); + PARAGRAPH_ID((short)3, "paragraphId"), + OBJECT((short)4, "object"); private static final Map byName = new HashMap(); @@ -10042,7 +10057,9 @@ public static _Fields findByThriftId(int fieldId) { return NAME; case 2: // NOTE_ID return NOTE_ID; - case 3: // OBJECT + case 3: // PARAGRAPH_ID + return PARAGRAPH_ID; + case 4: // OBJECT return OBJECT; default: return null; @@ -10091,6 +10108,8 @@ public String getFieldName() { new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); tmpMap.put(_Fields.NOTE_ID, new org.apache.thrift.meta_data.FieldMetaData("noteId", org.apache.thrift.TFieldRequirementType.DEFAULT, new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); + tmpMap.put(_Fields.PARAGRAPH_ID, new org.apache.thrift.meta_data.FieldMetaData("paragraphId", org.apache.thrift.TFieldRequirementType.DEFAULT, + new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); tmpMap.put(_Fields.OBJECT, new org.apache.thrift.meta_data.FieldMetaData("object", org.apache.thrift.TFieldRequirementType.DEFAULT, new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); metaDataMap = Collections.unmodifiableMap(tmpMap); @@ -10103,11 +10122,13 @@ public angularObjectUpdate_args() { public angularObjectUpdate_args( String name, String noteId, + String paragraphId, String object) { this(); this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; this.object = object; } @@ -10121,6 +10142,9 @@ public angularObjectUpdate_args(angularObjectUpdate_args other) { if (other.isSetNoteId()) { this.noteId = other.noteId; } + if (other.isSetParagraphId()) { + this.paragraphId = other.paragraphId; + } if (other.isSetObject()) { this.object = other.object; } @@ -10134,6 +10158,7 @@ public angularObjectUpdate_args deepCopy() { public void clear() { this.name = null; this.noteId = null; + this.paragraphId = null; this.object = null; } @@ -10185,6 +10210,30 @@ public void setNoteIdIsSet(boolean value) { } } + public String getParagraphId() { + return this.paragraphId; + } + + public angularObjectUpdate_args setParagraphId(String paragraphId) { + this.paragraphId = paragraphId; + return this; + } + + public void unsetParagraphId() { + this.paragraphId = null; + } + + /** Returns true if field paragraphId is set (has been assigned a value) and false otherwise */ + public boolean isSetParagraphId() { + return this.paragraphId != null; + } + + public void setParagraphIdIsSet(boolean value) { + if (!value) { + this.paragraphId = null; + } + } + public String getObject() { return this.object; } @@ -10227,6 +10276,14 @@ public void setFieldValue(_Fields field, Object value) { } break; + case PARAGRAPH_ID: + if (value == null) { + unsetParagraphId(); + } else { + setParagraphId((String)value); + } + break; + case OBJECT: if (value == null) { unsetObject(); @@ -10246,6 +10303,9 @@ public Object getFieldValue(_Fields field) { case NOTE_ID: return getNoteId(); + case PARAGRAPH_ID: + return getParagraphId(); + case OBJECT: return getObject(); @@ -10264,6 +10324,8 @@ public boolean isSet(_Fields field) { return isSetName(); case NOTE_ID: return isSetNoteId(); + case PARAGRAPH_ID: + return isSetParagraphId(); case OBJECT: return isSetObject(); } @@ -10301,6 +10363,15 @@ public boolean equals(angularObjectUpdate_args that) { return false; } + boolean this_present_paragraphId = true && this.isSetParagraphId(); + boolean that_present_paragraphId = true && that.isSetParagraphId(); + if (this_present_paragraphId || that_present_paragraphId) { + if (!(this_present_paragraphId && that_present_paragraphId)) + return false; + if (!this.paragraphId.equals(that.paragraphId)) + return false; + } + boolean this_present_object = true && this.isSetObject(); boolean that_present_object = true && that.isSetObject(); if (this_present_object || that_present_object) { @@ -10327,6 +10398,11 @@ public int hashCode() { if (present_noteId) list.add(noteId); + boolean present_paragraphId = true && (isSetParagraphId()); + list.add(present_paragraphId); + if (present_paragraphId) + list.add(paragraphId); + boolean present_object = true && (isSetObject()); list.add(present_object); if (present_object) @@ -10363,6 +10439,16 @@ public int compareTo(angularObjectUpdate_args other) { return lastComparison; } } + lastComparison = Boolean.valueOf(isSetParagraphId()).compareTo(other.isSetParagraphId()); + if (lastComparison != 0) { + return lastComparison; + } + if (isSetParagraphId()) { + lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.paragraphId, other.paragraphId); + if (lastComparison != 0) { + return lastComparison; + } + } lastComparison = Boolean.valueOf(isSetObject()).compareTo(other.isSetObject()); if (lastComparison != 0) { return lastComparison; @@ -10409,6 +10495,14 @@ public String toString() { } first = false; if (!first) sb.append(", "); + sb.append("paragraphId:"); + if (this.paragraphId == null) { + sb.append("null"); + } else { + sb.append(this.paragraphId); + } + first = false; + if (!first) sb.append(", "); sb.append("object:"); if (this.object == null) { sb.append("null"); @@ -10475,7 +10569,15 @@ public void read(org.apache.thrift.protocol.TProtocol iprot, angularObjectUpdate org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); } break; - case 3: // OBJECT + case 3: // PARAGRAPH_ID + if (schemeField.type == org.apache.thrift.protocol.TType.STRING) { + struct.paragraphId = iprot.readString(); + struct.setParagraphIdIsSet(true); + } else { + org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); + } + break; + case 4: // OBJECT if (schemeField.type == org.apache.thrift.protocol.TType.STRING) { struct.object = iprot.readString(); struct.setObjectIsSet(true); @@ -10508,6 +10610,11 @@ public void write(org.apache.thrift.protocol.TProtocol oprot, angularObjectUpdat oprot.writeString(struct.noteId); oprot.writeFieldEnd(); } + if (struct.paragraphId != null) { + oprot.writeFieldBegin(PARAGRAPH_ID_FIELD_DESC); + oprot.writeString(struct.paragraphId); + oprot.writeFieldEnd(); + } if (struct.object != null) { oprot.writeFieldBegin(OBJECT_FIELD_DESC); oprot.writeString(struct.object); @@ -10537,16 +10644,22 @@ public void write(org.apache.thrift.protocol.TProtocol prot, angularObjectUpdate if (struct.isSetNoteId()) { optionals.set(1); } - if (struct.isSetObject()) { + if (struct.isSetParagraphId()) { optionals.set(2); } - oprot.writeBitSet(optionals, 3); + if (struct.isSetObject()) { + optionals.set(3); + } + oprot.writeBitSet(optionals, 4); if (struct.isSetName()) { oprot.writeString(struct.name); } if (struct.isSetNoteId()) { oprot.writeString(struct.noteId); } + if (struct.isSetParagraphId()) { + oprot.writeString(struct.paragraphId); + } if (struct.isSetObject()) { oprot.writeString(struct.object); } @@ -10555,7 +10668,7 @@ public void write(org.apache.thrift.protocol.TProtocol prot, angularObjectUpdate @Override public void read(org.apache.thrift.protocol.TProtocol prot, angularObjectUpdate_args struct) throws org.apache.thrift.TException { TTupleProtocol iprot = (TTupleProtocol) prot; - BitSet incoming = iprot.readBitSet(3); + BitSet incoming = iprot.readBitSet(4); if (incoming.get(0)) { struct.name = iprot.readString(); struct.setNameIsSet(true); @@ -10565,6 +10678,10 @@ public void read(org.apache.thrift.protocol.TProtocol prot, angularObjectUpdate_ struct.setNoteIdIsSet(true); } if (incoming.get(2)) { + struct.paragraphId = iprot.readString(); + struct.setParagraphIdIsSet(true); + } + if (incoming.get(3)) { struct.object = iprot.readString(); struct.setObjectIsSet(true); } @@ -10826,7 +10943,8 @@ public static class angularObjectAdd_args implements org.apache.thrift.TBase, SchemeFactory> schemes = new HashMap, SchemeFactory>(); static { @@ -10836,13 +10954,15 @@ public static class angularObjectAdd_args implements org.apache.thrift.TBase byName = new HashMap(); @@ -10861,7 +10981,9 @@ public static _Fields findByThriftId(int fieldId) { return NAME; case 2: // NOTE_ID return NOTE_ID; - case 3: // OBJECT + case 3: // PARAGRAPH_ID + return PARAGRAPH_ID; + case 4: // OBJECT return OBJECT; default: return null; @@ -10910,6 +11032,8 @@ public String getFieldName() { new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); tmpMap.put(_Fields.NOTE_ID, new org.apache.thrift.meta_data.FieldMetaData("noteId", org.apache.thrift.TFieldRequirementType.DEFAULT, new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); + tmpMap.put(_Fields.PARAGRAPH_ID, new org.apache.thrift.meta_data.FieldMetaData("paragraphId", org.apache.thrift.TFieldRequirementType.DEFAULT, + new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); tmpMap.put(_Fields.OBJECT, new org.apache.thrift.meta_data.FieldMetaData("object", org.apache.thrift.TFieldRequirementType.DEFAULT, new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); metaDataMap = Collections.unmodifiableMap(tmpMap); @@ -10922,11 +11046,13 @@ public angularObjectAdd_args() { public angularObjectAdd_args( String name, String noteId, + String paragraphId, String object) { this(); this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; this.object = object; } @@ -10940,6 +11066,9 @@ public angularObjectAdd_args(angularObjectAdd_args other) { if (other.isSetNoteId()) { this.noteId = other.noteId; } + if (other.isSetParagraphId()) { + this.paragraphId = other.paragraphId; + } if (other.isSetObject()) { this.object = other.object; } @@ -10953,6 +11082,7 @@ public angularObjectAdd_args deepCopy() { public void clear() { this.name = null; this.noteId = null; + this.paragraphId = null; this.object = null; } @@ -11004,6 +11134,30 @@ public void setNoteIdIsSet(boolean value) { } } + public String getParagraphId() { + return this.paragraphId; + } + + public angularObjectAdd_args setParagraphId(String paragraphId) { + this.paragraphId = paragraphId; + return this; + } + + public void unsetParagraphId() { + this.paragraphId = null; + } + + /** Returns true if field paragraphId is set (has been assigned a value) and false otherwise */ + public boolean isSetParagraphId() { + return this.paragraphId != null; + } + + public void setParagraphIdIsSet(boolean value) { + if (!value) { + this.paragraphId = null; + } + } + public String getObject() { return this.object; } @@ -11046,6 +11200,14 @@ public void setFieldValue(_Fields field, Object value) { } break; + case PARAGRAPH_ID: + if (value == null) { + unsetParagraphId(); + } else { + setParagraphId((String)value); + } + break; + case OBJECT: if (value == null) { unsetObject(); @@ -11065,6 +11227,9 @@ public Object getFieldValue(_Fields field) { case NOTE_ID: return getNoteId(); + case PARAGRAPH_ID: + return getParagraphId(); + case OBJECT: return getObject(); @@ -11083,6 +11248,8 @@ public boolean isSet(_Fields field) { return isSetName(); case NOTE_ID: return isSetNoteId(); + case PARAGRAPH_ID: + return isSetParagraphId(); case OBJECT: return isSetObject(); } @@ -11120,6 +11287,15 @@ public boolean equals(angularObjectAdd_args that) { return false; } + boolean this_present_paragraphId = true && this.isSetParagraphId(); + boolean that_present_paragraphId = true && that.isSetParagraphId(); + if (this_present_paragraphId || that_present_paragraphId) { + if (!(this_present_paragraphId && that_present_paragraphId)) + return false; + if (!this.paragraphId.equals(that.paragraphId)) + return false; + } + boolean this_present_object = true && this.isSetObject(); boolean that_present_object = true && that.isSetObject(); if (this_present_object || that_present_object) { @@ -11146,6 +11322,11 @@ public int hashCode() { if (present_noteId) list.add(noteId); + boolean present_paragraphId = true && (isSetParagraphId()); + list.add(present_paragraphId); + if (present_paragraphId) + list.add(paragraphId); + boolean present_object = true && (isSetObject()); list.add(present_object); if (present_object) @@ -11182,6 +11363,16 @@ public int compareTo(angularObjectAdd_args other) { return lastComparison; } } + lastComparison = Boolean.valueOf(isSetParagraphId()).compareTo(other.isSetParagraphId()); + if (lastComparison != 0) { + return lastComparison; + } + if (isSetParagraphId()) { + lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.paragraphId, other.paragraphId); + if (lastComparison != 0) { + return lastComparison; + } + } lastComparison = Boolean.valueOf(isSetObject()).compareTo(other.isSetObject()); if (lastComparison != 0) { return lastComparison; @@ -11228,6 +11419,14 @@ public String toString() { } first = false; if (!first) sb.append(", "); + sb.append("paragraphId:"); + if (this.paragraphId == null) { + sb.append("null"); + } else { + sb.append(this.paragraphId); + } + first = false; + if (!first) sb.append(", "); sb.append("object:"); if (this.object == null) { sb.append("null"); @@ -11294,7 +11493,15 @@ public void read(org.apache.thrift.protocol.TProtocol iprot, angularObjectAdd_ar org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); } break; - case 3: // OBJECT + case 3: // PARAGRAPH_ID + if (schemeField.type == org.apache.thrift.protocol.TType.STRING) { + struct.paragraphId = iprot.readString(); + struct.setParagraphIdIsSet(true); + } else { + org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); + } + break; + case 4: // OBJECT if (schemeField.type == org.apache.thrift.protocol.TType.STRING) { struct.object = iprot.readString(); struct.setObjectIsSet(true); @@ -11327,6 +11534,11 @@ public void write(org.apache.thrift.protocol.TProtocol oprot, angularObjectAdd_a oprot.writeString(struct.noteId); oprot.writeFieldEnd(); } + if (struct.paragraphId != null) { + oprot.writeFieldBegin(PARAGRAPH_ID_FIELD_DESC); + oprot.writeString(struct.paragraphId); + oprot.writeFieldEnd(); + } if (struct.object != null) { oprot.writeFieldBegin(OBJECT_FIELD_DESC); oprot.writeString(struct.object); @@ -11356,16 +11568,22 @@ public void write(org.apache.thrift.protocol.TProtocol prot, angularObjectAdd_ar if (struct.isSetNoteId()) { optionals.set(1); } - if (struct.isSetObject()) { + if (struct.isSetParagraphId()) { optionals.set(2); } - oprot.writeBitSet(optionals, 3); + if (struct.isSetObject()) { + optionals.set(3); + } + oprot.writeBitSet(optionals, 4); if (struct.isSetName()) { oprot.writeString(struct.name); } if (struct.isSetNoteId()) { oprot.writeString(struct.noteId); } + if (struct.isSetParagraphId()) { + oprot.writeString(struct.paragraphId); + } if (struct.isSetObject()) { oprot.writeString(struct.object); } @@ -11374,7 +11592,7 @@ public void write(org.apache.thrift.protocol.TProtocol prot, angularObjectAdd_ar @Override public void read(org.apache.thrift.protocol.TProtocol prot, angularObjectAdd_args struct) throws org.apache.thrift.TException { TTupleProtocol iprot = (TTupleProtocol) prot; - BitSet incoming = iprot.readBitSet(3); + BitSet incoming = iprot.readBitSet(4); if (incoming.get(0)) { struct.name = iprot.readString(); struct.setNameIsSet(true); @@ -11384,6 +11602,10 @@ public void read(org.apache.thrift.protocol.TProtocol prot, angularObjectAdd_arg struct.setNoteIdIsSet(true); } if (incoming.get(2)) { + struct.paragraphId = iprot.readString(); + struct.setParagraphIdIsSet(true); + } + if (incoming.get(3)) { struct.object = iprot.readString(); struct.setObjectIsSet(true); } @@ -11645,6 +11867,7 @@ public static class angularObjectRemove_args implements org.apache.thrift.TBase< private static final org.apache.thrift.protocol.TField NAME_FIELD_DESC = new org.apache.thrift.protocol.TField("name", org.apache.thrift.protocol.TType.STRING, (short)1); private static final org.apache.thrift.protocol.TField NOTE_ID_FIELD_DESC = new org.apache.thrift.protocol.TField("noteId", org.apache.thrift.protocol.TType.STRING, (short)2); + private static final org.apache.thrift.protocol.TField PARAGRAPH_ID_FIELD_DESC = new org.apache.thrift.protocol.TField("paragraphId", org.apache.thrift.protocol.TType.STRING, (short)3); private static final Map, SchemeFactory> schemes = new HashMap, SchemeFactory>(); static { @@ -11654,11 +11877,13 @@ public static class angularObjectRemove_args implements org.apache.thrift.TBase< public String name; // required public String noteId; // required + public String paragraphId; // required /** The set of fields this struct contains, along with convenience methods for finding and manipulating them. */ public enum _Fields implements org.apache.thrift.TFieldIdEnum { NAME((short)1, "name"), - NOTE_ID((short)2, "noteId"); + NOTE_ID((short)2, "noteId"), + PARAGRAPH_ID((short)3, "paragraphId"); private static final Map byName = new HashMap(); @@ -11677,6 +11902,8 @@ public static _Fields findByThriftId(int fieldId) { return NAME; case 2: // NOTE_ID return NOTE_ID; + case 3: // PARAGRAPH_ID + return PARAGRAPH_ID; default: return null; } @@ -11724,6 +11951,8 @@ public String getFieldName() { new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); tmpMap.put(_Fields.NOTE_ID, new org.apache.thrift.meta_data.FieldMetaData("noteId", org.apache.thrift.TFieldRequirementType.DEFAULT, new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); + tmpMap.put(_Fields.PARAGRAPH_ID, new org.apache.thrift.meta_data.FieldMetaData("paragraphId", org.apache.thrift.TFieldRequirementType.DEFAULT, + new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING))); metaDataMap = Collections.unmodifiableMap(tmpMap); org.apache.thrift.meta_data.FieldMetaData.addStructMetaDataMap(angularObjectRemove_args.class, metaDataMap); } @@ -11733,11 +11962,13 @@ public angularObjectRemove_args() { public angularObjectRemove_args( String name, - String noteId) + String noteId, + String paragraphId) { this(); this.name = name; this.noteId = noteId; + this.paragraphId = paragraphId; } /** @@ -11750,6 +11981,9 @@ public angularObjectRemove_args(angularObjectRemove_args other) { if (other.isSetNoteId()) { this.noteId = other.noteId; } + if (other.isSetParagraphId()) { + this.paragraphId = other.paragraphId; + } } public angularObjectRemove_args deepCopy() { @@ -11760,6 +11994,7 @@ public angularObjectRemove_args deepCopy() { public void clear() { this.name = null; this.noteId = null; + this.paragraphId = null; } public String getName() { @@ -11810,6 +12045,30 @@ public void setNoteIdIsSet(boolean value) { } } + public String getParagraphId() { + return this.paragraphId; + } + + public angularObjectRemove_args setParagraphId(String paragraphId) { + this.paragraphId = paragraphId; + return this; + } + + public void unsetParagraphId() { + this.paragraphId = null; + } + + /** Returns true if field paragraphId is set (has been assigned a value) and false otherwise */ + public boolean isSetParagraphId() { + return this.paragraphId != null; + } + + public void setParagraphIdIsSet(boolean value) { + if (!value) { + this.paragraphId = null; + } + } + public void setFieldValue(_Fields field, Object value) { switch (field) { case NAME: @@ -11828,6 +12087,14 @@ public void setFieldValue(_Fields field, Object value) { } break; + case PARAGRAPH_ID: + if (value == null) { + unsetParagraphId(); + } else { + setParagraphId((String)value); + } + break; + } } @@ -11839,6 +12106,9 @@ public Object getFieldValue(_Fields field) { case NOTE_ID: return getNoteId(); + case PARAGRAPH_ID: + return getParagraphId(); + } throw new IllegalStateException(); } @@ -11854,6 +12124,8 @@ public boolean isSet(_Fields field) { return isSetName(); case NOTE_ID: return isSetNoteId(); + case PARAGRAPH_ID: + return isSetParagraphId(); } throw new IllegalStateException(); } @@ -11889,6 +12161,15 @@ public boolean equals(angularObjectRemove_args that) { return false; } + boolean this_present_paragraphId = true && this.isSetParagraphId(); + boolean that_present_paragraphId = true && that.isSetParagraphId(); + if (this_present_paragraphId || that_present_paragraphId) { + if (!(this_present_paragraphId && that_present_paragraphId)) + return false; + if (!this.paragraphId.equals(that.paragraphId)) + return false; + } + return true; } @@ -11906,6 +12187,11 @@ public int hashCode() { if (present_noteId) list.add(noteId); + boolean present_paragraphId = true && (isSetParagraphId()); + list.add(present_paragraphId); + if (present_paragraphId) + list.add(paragraphId); + return list.hashCode(); } @@ -11937,6 +12223,16 @@ public int compareTo(angularObjectRemove_args other) { return lastComparison; } } + lastComparison = Boolean.valueOf(isSetParagraphId()).compareTo(other.isSetParagraphId()); + if (lastComparison != 0) { + return lastComparison; + } + if (isSetParagraphId()) { + lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.paragraphId, other.paragraphId); + if (lastComparison != 0) { + return lastComparison; + } + } return 0; } @@ -11972,6 +12268,14 @@ public String toString() { sb.append(this.noteId); } first = false; + if (!first) sb.append(", "); + sb.append("paragraphId:"); + if (this.paragraphId == null) { + sb.append("null"); + } else { + sb.append(this.paragraphId); + } + first = false; sb.append(")"); return sb.toString(); } @@ -12031,6 +12335,14 @@ public void read(org.apache.thrift.protocol.TProtocol iprot, angularObjectRemove org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); } break; + case 3: // PARAGRAPH_ID + if (schemeField.type == org.apache.thrift.protocol.TType.STRING) { + struct.paragraphId = iprot.readString(); + struct.setParagraphIdIsSet(true); + } else { + org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); + } + break; default: org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); } @@ -12056,6 +12368,11 @@ public void write(org.apache.thrift.protocol.TProtocol oprot, angularObjectRemov oprot.writeString(struct.noteId); oprot.writeFieldEnd(); } + if (struct.paragraphId != null) { + oprot.writeFieldBegin(PARAGRAPH_ID_FIELD_DESC); + oprot.writeString(struct.paragraphId); + oprot.writeFieldEnd(); + } oprot.writeFieldStop(); oprot.writeStructEnd(); } @@ -12080,19 +12397,25 @@ public void write(org.apache.thrift.protocol.TProtocol prot, angularObjectRemove if (struct.isSetNoteId()) { optionals.set(1); } - oprot.writeBitSet(optionals, 2); + if (struct.isSetParagraphId()) { + optionals.set(2); + } + oprot.writeBitSet(optionals, 3); if (struct.isSetName()) { oprot.writeString(struct.name); } if (struct.isSetNoteId()) { oprot.writeString(struct.noteId); } + if (struct.isSetParagraphId()) { + oprot.writeString(struct.paragraphId); + } } @Override public void read(org.apache.thrift.protocol.TProtocol prot, angularObjectRemove_args struct) throws org.apache.thrift.TException { TTupleProtocol iprot = (TTupleProtocol) prot; - BitSet incoming = iprot.readBitSet(2); + BitSet incoming = iprot.readBitSet(3); if (incoming.get(0)) { struct.name = iprot.readString(); struct.setNameIsSet(true); @@ -12101,6 +12424,10 @@ public void read(org.apache.thrift.protocol.TProtocol prot, angularObjectRemove_ struct.noteId = iprot.readString(); struct.setNoteIdIsSet(true); } + if (incoming.get(2)) { + struct.paragraphId = iprot.readString(); + struct.setParagraphIdIsSet(true); + } } } diff --git a/zeppelin-interpreter/src/main/thrift/RemoteInterpreterService.thrift b/zeppelin-interpreter/src/main/thrift/RemoteInterpreterService.thrift index 65fd0a7027e..5cd14a2b765 100644 --- a/zeppelin-interpreter/src/main/thrift/RemoteInterpreterService.thrift +++ b/zeppelin-interpreter/src/main/thrift/RemoteInterpreterService.thrift @@ -67,7 +67,8 @@ service RemoteInterpreterService { string getStatus(1:string jobId); RemoteInterpreterEvent getEvent(); - void angularObjectUpdate(1: string name, 2: string noteId, 3: string object); - void angularObjectAdd(1: string name, 2: string noteId, 3: string object); - void angularObjectRemove(1: string name, 2: string noteId); + void angularObjectUpdate(1: string name, 2: string noteId, 3: string paragraphId, 4: string + object); + void angularObjectAdd(1: string name, 2: string noteId, 3: string paragraphId, 4: string object); + void angularObjectRemove(1: string name, 2: string noteId, 3: string paragraphId); } \ No newline at end of file diff --git a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectRegistryTest.java b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectRegistryTest.java index 43aca62c497..2d0436f205b 100644 --- a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectRegistryTest.java +++ b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectRegistryTest.java @@ -18,6 +18,8 @@ package org.apache.zeppelin.display; import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; import java.util.concurrent.atomic.AtomicInteger; @@ -45,32 +47,68 @@ public void onUpdate(String interpreterGroupId, AngularObject object) { } @Override - public void onRemove(String interpreterGroupId, String name, String noteId) { + public void onRemove(String interpreterGroupId, String name, String noteId, String paragraphId) { onRemove.incrementAndGet(); } }); - registry.add("name1", "value1", "note1"); - assertEquals(1, registry.getAll("note1").size()); + registry.add("name1", "value1", "note1", null); + assertEquals(1, registry.getAll("note1", null).size()); assertEquals(1, onAdd.get()); assertEquals(0, onUpdate.get()); - registry.get("name1", "note1").set("newValue"); + registry.get("name1", "note1", null).set("newValue"); assertEquals(1, onUpdate.get()); - registry.remove("name1", "note1"); - assertEquals(0, registry.getAll("note1").size()); + registry.remove("name1", "note1", null); + assertEquals(0, registry.getAll("note1", null).size()); assertEquals(1, onRemove.get()); - assertEquals(null, registry.get("name1", "note1")); + assertEquals(null, registry.get("name1", "note1", null)); // namespace - registry.add("name1", "value11", "note2"); - assertEquals("value11", registry.get("name1", "note2").get()); - assertEquals(null, registry.get("name1", "note1")); + registry.add("name1", "value11", "note2", null); + assertEquals("value11", registry.get("name1", "note2", null).get()); + assertEquals(null, registry.get("name1", "note1", null)); // null namespace - registry.add("name1", "global1", null); - assertEquals("global1", registry.get("name1", null).get()); + registry.add("name1", "global1", null, null); + assertEquals("global1", registry.get("name1", null, null).get()); } + + @Test + public void testGetDependOnScope() { + AngularObjectRegistry registry = new AngularObjectRegistry("intpId", null); + AngularObject ao1 = registry.add("name1", "o1", "noteId1", "paragraphId1"); + AngularObject ao2 = registry.add("name2", "o2", "noteId1", "paragraphId1"); + AngularObject ao3 = registry.add("name2", "o3", "noteId1", "paragraphId2"); + AngularObject ao4 = registry.add("name3", "o4", "noteId1", null); + AngularObject ao5 = registry.add("name4", "o5", null, null); + + + assertNull(registry.get("name3", "noteId1", "paragraphId1")); + assertNull(registry.get("name1", "noteId2", null)); + assertEquals("o1", registry.get("name1", "noteId1", "paragraphId1").get()); + assertEquals("o2", registry.get("name2", "noteId1", "paragraphId1").get()); + assertEquals("o3", registry.get("name2", "noteId1", "paragraphId2").get()); + assertEquals("o4", registry.get("name3", "noteId1", null).get()); + assertEquals("o5", registry.get("name4", null, null).get()); + } + + @Test + public void testGetAllDependOnScope() { + AngularObjectRegistry registry = new AngularObjectRegistry("intpId", null); + AngularObject ao1 = registry.add("name1", "o", "noteId1", "paragraphId1"); + AngularObject ao2 = registry.add("name2", "o", "noteId1", "paragraphId1"); + AngularObject ao3 = registry.add("name2", "o", "noteId1", "paragraphId2"); + AngularObject ao4 = registry.add("name3", "o", "noteId1", null); + AngularObject ao5 = registry.add("name4", "o", null, null); + + assertEquals(2, registry.getAll("noteId1", "paragraphId1").size()); + assertEquals(1, registry.getAll("noteId1", "paragraphId2").size()); + assertEquals(1, registry.getAll("noteId1", null).size()); + assertEquals(1, registry.getAll(null, null).size()); + assertEquals(5, registry.getAllWithGlobal("noteId1").size()); + } + } diff --git a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectTest.java b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectTest.java index acb93d041b6..924c5d4126c 100644 --- a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectTest.java +++ b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/display/AngularObjectTest.java @@ -18,6 +18,7 @@ package org.apache.zeppelin.display; import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotSame; import java.util.concurrent.atomic.AtomicInteger; @@ -26,10 +27,60 @@ public class AngularObjectTest { + @Test + public void testEquals() { + assertEquals( + new AngularObject("name", "value", "note1", null, null), + new AngularObject("name", "value", "note1", null, null) + ); + + assertEquals( + new AngularObject("name", "value", "note1", "paragraph1", null), + new AngularObject("name", "value", "note1", "paragraph1", null) + ); + + assertEquals( + new AngularObject("name", "value", null, null, null), + new AngularObject("name", "value", null, null, null) + ); + + assertEquals( + new AngularObject("name", "value1", null, null, null), + new AngularObject("name", "value2", null, null, null) + ); + + assertNotSame( + new AngularObject("name1", "value", null, null, null), + new AngularObject("name2", "value", null, null, null) + ); + + assertNotSame( + new AngularObject("name1", "value", "note1", null, null), + new AngularObject("name2", "value", "note2", null, null) + ); + + assertNotSame( + new AngularObject("name1", "value", "note", null, null), + new AngularObject("name2", "value", null, null, null) + ); + + assertNotSame( + new AngularObject("name", "value", "note", "paragraph1", null), + new AngularObject("name", "value", "note", "paragraph2", null) + ); + + assertNotSame( + new AngularObject("name", "value", "note1", null, null), + new AngularObject("name", "value", "note1", "paragraph1", null) + ); + + + } + @Test public void testListener() { final AtomicInteger updated = new AtomicInteger(0); - AngularObject ao = new AngularObject("name", "value", "note1", new AngularObjectListener() { + AngularObject ao = new AngularObject("name", "value", "note1", null, new AngularObjectListener() { @Override public void updated(AngularObject updatedObject) { @@ -55,7 +106,7 @@ public void updated(AngularObject updatedObject) { public void testWatcher() throws InterruptedException { final AtomicInteger updated = new AtomicInteger(0); final AtomicInteger onWatch = new AtomicInteger(0); - AngularObject ao = new AngularObject("name", "value", "note1", new AngularObjectListener() { + AngularObject ao = new AngularObject("name", "value", "note1", null, new AngularObjectListener() { @Override public void updated(AngularObject updatedObject) { updated.incrementAndGet(); diff --git a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectTest.java b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectTest.java index 906878d2b7e..4cd974dbb3c 100644 --- a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectTest.java +++ b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/RemoteAngularObjectTest.java @@ -110,7 +110,7 @@ public void testAngularObjectInterpreterSideCRUD() throws InterruptedException { result = ret.message().split(" "); assertEquals("1", result[0]); // size of registry assertEquals("0", result[1]); // num watcher called - assertEquals("v1", localRegistry.get("n1", "note").get()); + assertEquals("v1", localRegistry.get("n1", "note", null).get()); // update object ret = intp.interpret("update n1 v11", context); @@ -118,7 +118,7 @@ public void testAngularObjectInterpreterSideCRUD() throws InterruptedException { Thread.sleep(500); assertEquals("1", result[0]); // size of registry assertEquals("1", result[1]); // num watcher called - assertEquals("v11", localRegistry.get("n1", "note").get()); + assertEquals("v11", localRegistry.get("n1", "note", null).get()); // remove object ret = intp.interpret("remove n1", context); @@ -126,7 +126,7 @@ public void testAngularObjectInterpreterSideCRUD() throws InterruptedException { Thread.sleep(500); assertEquals("0", result[0]); // size of registry assertEquals("1", result[1]); // num watcher called - assertEquals(null, localRegistry.get("n1", "note")); + assertEquals(null, localRegistry.get("n1", "note", null)); } @Test @@ -144,10 +144,10 @@ public void testAngularObjectRemovalOnZeppelinServerSide() throws InterruptedExc Thread.sleep(500); result = ret.message().split(" "); assertEquals("1", result[0]); // size of registry - assertEquals("v1", localRegistry.get("n1", "note").get()); + assertEquals("v1", localRegistry.get("n1", "note", null).get()); // remove object in local registry. - localRegistry.removeAndNotifyRemoteProcess("n1", "note"); + localRegistry.removeAndNotifyRemoteProcess("n1", "note", null); ret = intp.interpret("get", context); Thread.sleep(500); // waitFor eventpoller pool event result = ret.message().split(" "); @@ -165,7 +165,7 @@ public void testAngularObjectAddOnZeppelinServerSide() throws InterruptedExcepti assertEquals("0", result[0]); // size of registry // create object - localRegistry.addAndNotifyRemoteProcess("n1", "v1", "note"); + localRegistry.addAndNotifyRemoteProcess("n1", "v1", "note", null); // get from remote registry ret = intp.interpret("get", context); @@ -185,7 +185,7 @@ public void onUpdate(String interpreterGroupId, AngularObject object) { } @Override - public void onRemove(String interpreterGroupId, String name, String noteId) { + public void onRemove(String interpreterGroupId, String name, String noteId, String paragraphId) { onRemove.incrementAndGet(); } diff --git a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/mock/MockInterpreterAngular.java b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/mock/MockInterpreterAngular.java index 7c1a2f0614c..2f448f27873 100644 --- a/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/mock/MockInterpreterAngular.java +++ b/zeppelin-interpreter/src/test/java/org/apache/zeppelin/interpreter/remote/mock/MockInterpreterAngular.java @@ -71,8 +71,9 @@ public InterpreterResult interpret(String st, InterpreterContext context) { AngularObjectRegistry registry = context.getAngularObjectRegistry(); if (cmd.equals("add")) { - registry.add(name, value, context.getNoteId()); - registry.get(name, context.getNoteId()).addWatcher(new AngularObjectWatcher(null) { + registry.add(name, value, context.getNoteId(), null); + registry.get(name, context.getNoteId(), null).addWatcher(new AngularObjectWatcher + (null) { @Override public void watch(Object oldObject, Object newObject, @@ -82,9 +83,9 @@ public void watch(Object oldObject, Object newObject, }); } else if (cmd.equalsIgnoreCase("update")) { - registry.get(name, context.getNoteId()).set(value); + registry.get(name, context.getNoteId(), null).set(value); } else if (cmd.equals("remove")) { - registry.remove(name, context.getNoteId()); + registry.remove(name, context.getNoteId(), null); } try { @@ -93,7 +94,8 @@ public void watch(Object oldObject, Object newObject, logger.error("Exception in MockInterpreterAngular while interpret Thread.sleep", e); } - String msg = registry.getAll(context.getNoteId()).size() + " " + Integer.toString(numWatch.get()); + String msg = registry.getAll(context.getNoteId(), null).size() + " " + Integer.toString(numWatch + .get()); return new InterpreterResult(Code.SUCCESS, msg); } diff --git a/zeppelin-server/src/main/java/org/apache/zeppelin/socket/NotebookServer.java b/zeppelin-server/src/main/java/org/apache/zeppelin/socket/NotebookServer.java index 64698fcdfd4..fee4f40b71e 100644 --- a/zeppelin-server/src/main/java/org/apache/zeppelin/socket/NotebookServer.java +++ b/zeppelin-server/src/main/java/org/apache/zeppelin/socket/NotebookServer.java @@ -602,6 +602,7 @@ private void completion(NotebookSocket conn, Notebook notebook, private void angularObjectUpdated(NotebookSocket conn, Notebook notebook, Message fromMessage) { String noteId = (String) fromMessage.get("noteId"); + String paragraphId = (String) fromMessage.get("paragraphId"); String interpreterGroupId = (String) fromMessage.get("interpreterGroupId"); String varName = (String) fromMessage.get("name"); Object varValue = fromMessage.get("value"); @@ -620,19 +621,26 @@ private void angularObjectUpdated(NotebookSocket conn, Notebook notebook, AngularObjectRegistry angularObjectRegistry = setting .getInterpreterGroup().getAngularObjectRegistry(); // first trying to get local registry - ao = angularObjectRegistry.get(varName, noteId); + ao = angularObjectRegistry.get(varName, noteId, paragraphId); if (ao == null) { - // then try global registry - ao = angularObjectRegistry.get(varName, null); + // then try notebook scope registry + ao = angularObjectRegistry.get(varName, noteId, null); if (ao == null) { - LOG.warn("Object {} is not binded", varName); + // then try global scope registry + ao = angularObjectRegistry.get(varName, null, null); + if (ao == null) { + LOG.warn("Object {} is not binded", varName); + } else { + // path from client -> server + ao.set(varValue, false); + global = true; + } } else { // path from client -> server ao.set(varValue, false); - global = true; + global = false; } } else { - // path from client -> server ao.set(varValue, false); global = false; } @@ -657,7 +665,8 @@ private void angularObjectUpdated(NotebookSocket conn, Notebook notebook, n.id(), new Message(OP.ANGULAR_OBJECT_UPDATE).put("angularObject", ao) .put("interpreterGroupId", interpreterGroupId) - .put("noteId", n.id()), + .put("noteId", n.id()) + .put("paragraphId", ao.getParagraphId()), conn); } } @@ -667,7 +676,8 @@ private void angularObjectUpdated(NotebookSocket conn, Notebook notebook, note.id(), new Message(OP.ANGULAR_OBJECT_UPDATE).put("angularObject", ao) .put("interpreterGroupId", interpreterGroupId) - .put("noteId", note.id()), + .put("noteId", note.id()) + .put("paragraphId", ao.getParagraphId()), conn); } } @@ -878,7 +888,9 @@ private void sendAllAngularObjects(Note note, NotebookSocket conn) throws IOExce .put("angularObject", object) .put("interpreterGroupId", intpSetting.getInterpreterGroup().getId()) - .put("noteId", note.id()))); + .put("noteId", note.id()) + .put("paragraphId", object.getParagraphId()) + )); } } } @@ -912,14 +924,15 @@ public void onUpdate(String interpreterGroupId, AngularObject object) { new Message(OP.ANGULAR_OBJECT_UPDATE) .put("angularObject", object) .put("interpreterGroupId", interpreterGroupId) - .put("noteId", note.id())); + .put("noteId", note.id()) + .put("paragraphId", object.getParagraphId())); } } } } @Override - public void onRemove(String interpreterGroupId, String name, String noteId) { + public void onRemove(String interpreterGroupId, String name, String noteId, String paragraphId) { Notebook notebook = notebook(); List notes = notebook.getAllNotes(); for (Note note : notes) { @@ -933,7 +946,7 @@ public void onRemove(String interpreterGroupId, String name, String noteId) { broadcast( note.id(), new Message(OP.ANGULAR_OBJECT_REMOVE).put("name", name).put( - "noteId", noteId)); + "noteId", noteId).put("paragraphId", paragraphId)); } } } diff --git a/zeppelin-server/src/test/java/org/apache/zeppelin/socket/NotebookServerTest.java b/zeppelin-server/src/test/java/org/apache/zeppelin/socket/NotebookServerTest.java index 8ec7bddb2d8..7d8f3cf710f 100644 --- a/zeppelin-server/src/test/java/org/apache/zeppelin/socket/NotebookServerTest.java +++ b/zeppelin-server/src/test/java/org/apache/zeppelin/socket/NotebookServerTest.java @@ -45,8 +45,6 @@ * BASIC Zeppelin rest api tests */ public class NotebookServerTest extends AbstractTestRestApi { - - private static Notebook notebook; private static NotebookServer notebookServer; private static Gson gson; @@ -97,7 +95,7 @@ public void testMakeSureNoAngularObjectBroadcastToWebsocketWhoFireTheEvent() thr } // add angularObject - interpreterGroup.getAngularObjectRegistry().add("object1", "value1", note1.getId()); + interpreterGroup.getAngularObjectRegistry().add("object1", "value1", note1.getId(), null); // create two sockets and open it NotebookSocket sock1 = createWebSocket(); diff --git a/zeppelin-web/src/app/app.controller.js b/zeppelin-web/src/app/app.controller.js index 2c302b542d9..ce466a7c89d 100644 --- a/zeppelin-web/src/app/app.controller.js +++ b/zeppelin-web/src/app/app.controller.js @@ -14,7 +14,6 @@ 'use strict'; angular.module('zeppelinWebApp').controller('MainCtrl', function($scope, $rootScope, $window) { - $rootScope.compiledScope = $scope.$new(true, $rootScope); $scope.looknfeel = 'default'; var init = function() { diff --git a/zeppelin-web/src/app/notebook/notebook.controller.js b/zeppelin-web/src/app/notebook/notebook.controller.js index e10d725308e..5919e4ef96a 100644 --- a/zeppelin-web/src/app/notebook/notebook.controller.js +++ b/zeppelin-web/src/app/notebook/notebook.controller.js @@ -41,7 +41,6 @@ angular.module('zeppelinWebApp').controller('NotebookCtrl', $scope.isNoteDirty = null; $scope.saveTimer = null; - var angularObjectRegistry = {}; var connectedOnce = false; $scope.$on('setConnectedStatus', function(event, param) { @@ -625,52 +624,4 @@ angular.module('zeppelinWebApp').controller('NotebookCtrl', return true; } }; - - $scope.$on('angularObjectUpdate', function(event, data) { - if (data.noteId === $scope.note.id) { - var scope = $rootScope.compiledScope; - var varName = data.angularObject.name; - - if (angular.equals(data.angularObject.object, scope[varName])) { - // return when update has no change - return; - } - - if (!angularObjectRegistry[varName]) { - angularObjectRegistry[varName] = { - interpreterGroupId : data.interpreterGroupId, - }; - } - - angularObjectRegistry[varName].skipEmit = true; - - if (!angularObjectRegistry[varName].clearWatcher) { - angularObjectRegistry[varName].clearWatcher = scope.$watch(varName, function(newValue, oldValue) { - if (angularObjectRegistry[varName].skipEmit) { - angularObjectRegistry[varName].skipEmit = false; - return; - } - websocketMsgSrv.updateAngularObject($routeParams.noteId, varName, newValue, angularObjectRegistry[varName].interpreterGroupId); - }); - } - scope[varName] = data.angularObject.object; - } - }); - - $scope.$on('angularObjectRemove', function(event, data) { - if (!data.noteId || data.noteId === $scope.note.id) { - var scope = $rootScope.compiledScope; - var varName = data.name; - - // clear watcher - if (angularObjectRegistry[varName]) { - angularObjectRegistry[varName].clearWatcher(); - angularObjectRegistry[varName] = undefined; - } - - // remove scope variable - scope[varName] = undefined; - } - }); - }); diff --git a/zeppelin-web/src/app/notebook/paragraph/paragraph.controller.js b/zeppelin-web/src/app/notebook/paragraph/paragraph.controller.js index 30c7ea44015..458432f89fd 100644 --- a/zeppelin-web/src/app/notebook/paragraph/paragraph.controller.js +++ b/zeppelin-web/src/app/notebook/paragraph/paragraph.controller.js @@ -17,10 +17,12 @@ angular.module('zeppelinWebApp') .controller('ParagraphCtrl', function($scope,$rootScope, $route, $window, $element, $routeParams, $location, $timeout, $compile, websocketMsgSrv) { - + var ANGULAR_FUNCTION_OBJECT_NAME_PREFIX = '_Z_ANGULAR_FUNC_'; $scope.paragraph = null; $scope.originalText = ''; $scope.editor = null; + var paragraphScope = $rootScope.$new(true, $rootScope); + var angularObjectRegistry = {}; var editorModes = { 'ace/mode/scala': /^%spark/, @@ -84,7 +86,7 @@ angular.module('zeppelinWebApp') try { angular.element('#p'+$scope.paragraph.id+'_angular').html($scope.paragraph.result.msg); - $compile(angular.element('#p'+$scope.paragraph.id+'_angular').contents())($rootScope.compiledScope); + $compile(angular.element('#p'+$scope.paragraph.id+'_angular').contents())(paragraphScope); } catch(err) { console.log('ANGULAR rendering error %o', err); } @@ -132,6 +134,85 @@ angular.module('zeppelinWebApp') + $scope.$on('angularObjectUpdate', function(event, data) { + var noteId = $route.current.pathParams.noteId; + if (!data.noteId || (data.noteId === noteId && (!data.paragraphId || data.paragraphId === $scope.paragraph.id))) { + var scope = paragraphScope; + var varName = data.angularObject.name; + + if (angular.equals(data.angularObject.object, scope[varName])) { + // return when update has no change + return; + } + + if (!angularObjectRegistry[varName]) { + angularObjectRegistry[varName] = { + interpreterGroupId : data.interpreterGroupId, + noteId : data.noteId, + paragraphId : data.paragraphId + }; + } else { + angularObjectRegistry[varName].noteId = angularObjectRegistry[varName].noteId || data.noteId; + angularObjectRegistry[varName].paragraphId = angularObjectRegistry[varName].paragraphId || data.paragraphId; + } + + angularObjectRegistry[varName].skipEmit = true; + + if (!angularObjectRegistry[varName].clearWatcher) { + angularObjectRegistry[varName].clearWatcher = scope.$watch(varName, function(newValue, oldValue) { + console.log('angular object (paragraph) updated %o %o', varName, angularObjectRegistry[varName]); + if (angularObjectRegistry[varName].skipEmit) { + angularObjectRegistry[varName].skipEmit = false; + return; + } + websocketMsgSrv.updateAngularObject( + angularObjectRegistry[varName].noteId, + angularObjectRegistry[varName].paragraphId, + varName, + newValue, + angularObjectRegistry[varName].interpreterGroupId); + }); + } + console.log('angular object (paragraph) created %o', varName); + scope[varName] = data.angularObject.object; + + // create proxy for AngularFunction + if (varName.startsWith(ANGULAR_FUNCTION_OBJECT_NAME_PREFIX)) { + var funcName = varName.substring((ANGULAR_FUNCTION_OBJECT_NAME_PREFIX).length); + scope[funcName] = function() { + scope[varName] = arguments; + console.log('angular function (paragraph) invoked %o', arguments); + }; + + console.log('angular function (paragraph) created %o', scope[funcName]); + } + } + }); + + + $scope.$on('angularObjectRemove', function(event, data) { + var noteId = $route.current.pathParams.noteId; + if (!data.noteId || (data.noteId === noteId && (!data.paragraphId || data.paragraphId === $scope.paragraph.id))) { + var scope = paragraphScope; + var varName = data.name; + + // clear watcher + if (angularObjectRegistry[varName]) { + angularObjectRegistry[varName].clearWatcher(); + angularObjectRegistry[varName] = undefined; + } + + // remove scope variable + scope[varName] = undefined; + + // remove proxy for AngularFunction + if (varName.startsWith(ANGULAR_FUNCTION_OBJECT_NAME_PREFIX)) { + var funcName = varName.substring((ANGULAR_FUNCTION_OBJECT_NAME_PREFIX).length); + scope[funcName] = undefined; + } + } + }); + var initializeDefault = function() { var config = $scope.paragraph.config; diff --git a/zeppelin-web/src/components/websocketEvents/websocketMsg.service.js b/zeppelin-web/src/components/websocketEvents/websocketMsg.service.js index b8f22045d89..df440100942 100644 --- a/zeppelin-web/src/components/websocketEvents/websocketMsg.service.js +++ b/zeppelin-web/src/components/websocketEvents/websocketMsg.service.js @@ -57,11 +57,12 @@ angular.module('zeppelinWebApp').service('websocketMsgSrv', function($rootScope, websocketEvents.sendNewEvent({ op: 'INSERT_PARAGRAPH', data : {index: newIndex}}); }, - updateAngularObject: function(noteId, name, value, interpreterGroupId) { + updateAngularObject: function(noteId, paragraphId, name, value, interpreterGroupId) { websocketEvents.sendNewEvent({ op: 'ANGULAR_OBJECT_UPDATED', data: { noteId: noteId, + paragraphId: paragraphId, name: name, value: value, interpreterGroupId: interpreterGroupId diff --git a/zeppelin-web/test/spec/controllers/paragraph.js b/zeppelin-web/test/spec/controllers/paragraph.js index 25716c13a8c..7cdf74876f1 100644 --- a/zeppelin-web/test/spec/controllers/paragraph.js +++ b/zeppelin-web/test/spec/controllers/paragraph.js @@ -13,6 +13,8 @@ describe('Controller: ParagraphCtrl', function() { beforeEach(inject(function($controller, $rootScope) { scope = $rootScope.$new(); + $rootScope.notebookScope = $rootScope.$new(true, $rootScope); + ParagraphCtrl = $controller('ParagraphCtrl', { $scope: scope, websocketMsgSrv: websocketMsgSrvMock, @@ -79,4 +81,4 @@ describe('Controller: ParagraphCtrl', function() { expect(scope.renderAngular).toHaveBeenCalled(); }); -}); \ No newline at end of file +}); diff --git a/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Note.java b/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Note.java index 10f080dd03a..27e2f77cee2 100644 --- a/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Note.java +++ b/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Note.java @@ -218,6 +218,8 @@ public Paragraph removeParagraph(String paragraphId) { } } } + + removeAllAngularObjectInParagraph(paragraphId); return null; } @@ -400,6 +402,21 @@ private void snapshotAngularObjectRegistry() { } } + private void removeAllAngularObjectInParagraph(String paragraphId) { + angularObjects = new HashMap>(); + + List settings = replLoader.getInterpreterSettings(); + if (settings == null || settings.size() == 0) { + return; + } + + for (InterpreterSetting setting : settings) { + InterpreterGroup intpGroup = setting.getInterpreterGroup(); + AngularObjectRegistry registry = intpGroup.getAngularObjectRegistry(); + registry.removeAll(id, paragraphId); + } + } + public void persist() throws IOException { stopDelayedPersistTimer(); snapshotAngularObjectRegistry(); diff --git a/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Notebook.java b/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Notebook.java index a068cea8ed2..0637e53fcab 100644 --- a/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Notebook.java +++ b/zeppelin-zengine/src/main/java/org/apache/zeppelin/notebook/Notebook.java @@ -228,9 +228,9 @@ public void removeNote(String id) { for (InterpreterSetting settings : replFactory.get()) { AngularObjectRegistry registry = settings.getInterpreterGroup().getAngularObjectRegistry(); if (registry instanceof RemoteAngularObjectRegistry) { - ((RemoteAngularObjectRegistry) registry).removeAllAndNotifyRemoteProcess(id); + ((RemoteAngularObjectRegistry) registry).removeAllAndNotifyRemoteProcess(id, null); } else { - registry.removeAll(id); + registry.removeAll(id, null); } } @@ -304,12 +304,13 @@ private Note loadNoteFromRepo(String id) { if (intpGroup.getId().equals(snapshot.getIntpGroupId())) { AngularObjectRegistry registry = intpGroup.getAngularObjectRegistry(); String noteId = snapshot.getAngularObject().getNoteId(); + String paragraphId = snapshot.getAngularObject().getParagraphId(); // at this point, remote interpreter process is not created. // so does not make sense add it to the remote. // // therefore instead of addAndNotifyRemoteProcess(), need to use add() // that results add angularObject only in ZeppelinServer side not remoteProcessSide - registry.add(name, snapshot.getAngularObject().get(), noteId); + registry.add(name, snapshot.getAngularObject().get(), noteId, paragraphId); } } } diff --git a/zeppelin-zengine/src/test/java/org/apache/zeppelin/notebook/NotebookTest.java b/zeppelin-zengine/src/test/java/org/apache/zeppelin/notebook/NotebookTest.java index 82ba1371ea5..506b682b293 100644 --- a/zeppelin-zengine/src/test/java/org/apache/zeppelin/notebook/NotebookTest.java +++ b/zeppelin-zengine/src/test/java/org/apache/zeppelin/notebook/NotebookTest.java @@ -321,17 +321,17 @@ public void testAngularObjectRemovalOnNotebookRemove() throws InterruptedExcepti .getAngularObjectRegistry(); // add local scope object - registry.add("o1", "object1", note.id()); + registry.add("o1", "object1", note.id(), null); // add global scope object - registry.add("o2", "object2", null); + registry.add("o2", "object2", null, null); // remove notebook notebook.removeNote(note.id()); // local object should be removed - assertNull(registry.get("o1", note.id())); + assertNull(registry.get("o1", note.id(), null)); // global object sould be remained - assertNotNull(registry.get("o2", null)); + assertNotNull(registry.get("o2", null, null)); } @Test @@ -346,9 +346,9 @@ public void testAngularObjectRemovalOnInterpreterRestart() throws InterruptedExc .getAngularObjectRegistry(); // add local scope object - registry.add("o1", "object1", note.id()); + registry.add("o1", "object1", note.id(), null); // add global scope object - registry.add("o2", "object2", null); + registry.add("o2", "object2", null, null); // restart interpreter factory.restart(note.getNoteReplLoader().getInterpreterSettings().get(0).id()); @@ -357,8 +357,8 @@ public void testAngularObjectRemovalOnInterpreterRestart() throws InterruptedExc .getAngularObjectRegistry(); // local and global scope object should be removed - assertNull(registry.get("o1", note.id())); - assertNull(registry.get("o2", null)); + assertNull(registry.get("o1", note.id(), null)); + assertNull(registry.get("o2", null, null)); notebook.removeNote(note.id()); }