]> gerrit.simantics Code Review - simantics/platform.git/blobdiff - bundles/org.simantics.db.layer0/src/org/simantics/db/layer0/adapter/impl/DefaultPasteHandler.java
Prevent paste to resources that are `L0.Entity_published`
[simantics/platform.git] / bundles / org.simantics.db.layer0 / src / org / simantics / db / layer0 / adapter / impl / DefaultPasteHandler.java
index 874005f507e89084de832d5ca5f765790a9fa85d..067ed9207fe4d224f2add76b0ae00d71e098b51d 100644 (file)
-/*******************************************************************************\r
- * Copyright (c) 2007, 2010 Association for Decentralized Information Management\r
- * in Industry THTH ry.\r
- * All rights reserved. This program and the accompanying materials\r
- * are made available under the terms of the Eclipse Public License v1.0\r
- * which accompanies this distribution, and is available at\r
- * http://www.eclipse.org/legal/epl-v10.html\r
- *\r
- * Contributors:\r
- *     VTT Technical Research Centre of Finland - initial API and implementation\r
- *******************************************************************************/\r
-package org.simantics.db.layer0.adapter.impl;\r
-\r
-import java.util.ArrayList;\r
-import java.util.Collection;\r
-import java.util.Collections;\r
-import java.util.HashSet;\r
-import java.util.Map;\r
-import java.util.Set;\r
-\r
-import org.simantics.db.ReadGraph;\r
-import org.simantics.db.Resource;\r
-import org.simantics.db.WriteGraph;\r
-import org.simantics.db.exception.DatabaseException;\r
-import org.simantics.db.layer0.adapter.PasteHandlerAdapter;\r
-import org.simantics.db.layer0.internal.SimanticsInternal;\r
-import org.simantics.db.layer0.util.ClipboardUtils;\r
-import org.simantics.db.layer0.util.ModelTransferableGraphSource;\r
-import org.simantics.db.layer0.util.PasteEventHandler;\r
-import org.simantics.db.layer0.util.RemoverUtil;\r
-import org.simantics.db.layer0.util.SimanticsClipboard;\r
-import org.simantics.db.layer0.util.SimanticsClipboard.Representation;\r
-import org.simantics.db.layer0.util.SimanticsKeys;\r
-import org.simantics.db.layer0.util.TransferableGraphConfiguration2.RootSpec;\r
-import org.simantics.graph.db.IImportAdvisor;\r
-import org.simantics.graph.db.IImportAdvisor2;\r
-import org.simantics.graph.db.IImportAdvisor2.RootInfo;\r
-import org.simantics.graph.db.TransferableGraphException;\r
-import org.simantics.graph.db.TransferableGraphSource;\r
-import org.simantics.graph.db.TransferableGraphs;\r
-import org.simantics.graph.representation.Identity;\r
-import org.simantics.graph.representation.Root;\r
-import org.simantics.graph.representation.TransferableGraph1;\r
-import org.simantics.graph.representation.TransferableGraphUtils;\r
-import org.simantics.layer0.Layer0;\r
-\r
-public class DefaultPasteHandler extends PasteHandlerAdapter {\r
-\r
-    protected Resource resource;\r
-\r
-    public DefaultPasteHandler(Resource resource) {\r
-        this.resource = resource;\r
-    }\r
-\r
-    public static void defaultExecute(TransferableGraph1 tg, Resource resource, IImportAdvisor advisor) throws DatabaseException, TransferableGraphException {\r
-        TransferableGraphs.importGraph1(SimanticsInternal.getSession(), tg, advisor);\r
-    }\r
-\r
-    public static void defaultExecute(WriteGraph graph, TransferableGraph1 tg, Resource resource, IImportAdvisor advisor) throws DatabaseException {\r
-        TransferableGraphs.importGraph1(graph, tg, advisor);\r
-    }\r
-\r
-    public void execute(WriteGraph graph, TransferableGraph1 tg, Resource resource, IImportAdvisor advisor) throws DatabaseException {\r
-       defaultExecute(graph, tg, resource, advisor);\r
-    }\r
-\r
-    /**\r
-     * Override this in your inherited class if post processing is done.\r
-     */\r
-    public void onPasteBegin(WriteGraph graph) throws DatabaseException {\r
-    }\r
-\r
-    /**\r
-     * Override this in your inherited class if post processing is done\r
-     * advisor.getTarget() returns an object under which data is copied\r
-     * advisor.getRoot() returns the object which have been pasted.\r
-     * @param representations TODO\r
-     */\r
-    public void onPaste(WriteGraph graph, IImportAdvisor2 advisor, Set<Representation> representations) throws DatabaseException {\r
-    }\r
-\r
-    /**\r
-     * Override this in your inherited class if post processing is done.\r
-     */\r
-    public void onPasteEnd(WriteGraph graph) throws DatabaseException {\r
-    }\r
-    \r
-    public IImportAdvisor2 getAdvisor(ReadGraph graph, TransferableGraph1 tg, Resource target, PasteEventHandler handler) throws DatabaseException {\r
-       \r
-       Collection<Identity> roots = TransferableGraphUtils.getRoots(tg);\r
-       if(roots.size() == 1) {\r
-               Root root = (Root)roots.iterator().next().definition;\r
-               Resource type = graph.getPossibleResource(root.type);\r
-               ImportAdvisorFactory factory = graph.getPossibleAdapter(type, ImportAdvisorFactory.class);\r
-               if(factory != null) {\r
-                       if(handler != null)\r
-                               return handler.createAdvisor(graph, factory, target);\r
-                       else\r
-                               return factory.create(graph, target, Collections.<String,Object>emptyMap());\r
-               }\r
-       }\r
-\r
-       return new DefaultPasteImportAdvisor(target);\r
-    }\r
-\r
-    public Collection<Resource> pasteObject(WriteGraph graph, Set<Representation> object, PasteEventHandler handler) throws DatabaseException {\r
-       Collection<Resource> result = new ArrayList<>();\r
-        TransferableGraphSource tgs = ClipboardUtils.accept(graph, object, SimanticsKeys.KEY_TRANSFERABLE_GRAPH_SOURCE);\r
-        if (tgs != null) {\r
-               TransferableGraph1 tg = TransferableGraphs.create(graph, tgs);\r
-            IImportAdvisor2 advisor = getAdvisor(graph, tg, resource, handler); \r
-            execute(graph, tg, resource, advisor);\r
-            Collection<RootInfo> roots = advisor.getRootInfo();\r
-            if(handler != null) {\r
-               for(RootInfo r : roots) handler.postProcess(graph, r.resource);\r
-            }\r
-            onPaste(graph, advisor, object);\r
-            if(tgs instanceof ModelTransferableGraphSource) {\r
-               \r
-               ModelTransferableGraphSource mtgs = (ModelTransferableGraphSource)tgs;\r
-               \r
-               loop: for(RootSpec spec : mtgs.getConfiguration().roots) {\r
-                       if(!spec.internal) continue;\r
-                       for(RootInfo info : roots) {\r
-                               if(spec.name.equals(info.root.name)) {\r
-                                       result.add(info.resource);\r
-                                       continue loop;\r
-                               }\r
-                       }\r
-                               // Fallback\r
-                               result.clear();\r
-                               result.addAll(advisor.getRoots());\r
-                               break;\r
-               }\r
-               \r
-            } else {\r
-               result.addAll(advisor.getRoots());\r
-            }\r
-        }\r
-        return result;\r
-    }\r
-\r
-    @Override\r
-    public Collection<Resource> pasteFromClipboard(WriteGraph graph, SimanticsClipboard clipboard, PasteEventHandler handler) throws DatabaseException {\r
-        \r
-       Collection<Resource> result = new ArrayList<>();\r
-       \r
-       Map<String,Object> hints = Collections.singletonMap(ClipboardUtils.HINT_TARGET_RESOURCE, resource);\r
-       \r
-        onPasteBegin(graph);\r
-\r
-        final Set<Resource> cuts = new HashSet<>();\r
-        for(Set<Representation> object : clipboard.getContents()) {\r
-            Collection<Resource> cut = ClipboardUtils.accept(object, SimanticsKeys.KEY_CUT_RESOURCES);\r
-            TransferableGraphSource tg = ClipboardUtils.accept(graph, object, SimanticsKeys.KEY_TRANSFERABLE_GRAPH_SOURCE, hints);\r
-            if(tg != null) {\r
-               result.addAll(pasteObject(graph, object, handler));\r
-               if (cut != null)\r
-                    cuts.addAll(cut);\r
-            } else {\r
-               Layer0 L0 = Layer0.getInstance(graph);\r
-               for(Resource r : cut) {\r
-                       graph.deny(r, L0.PartOf);\r
-                       graph.claim(resource, L0.ConsistsOf, L0.PartOf, r);\r
-                       result.add(r);\r
-               }\r
-            }\r
-        }\r
-\r
-        onPasteEnd(graph);\r
-\r
-        if(!cuts.isEmpty()) {\r
-               for (Resource cut : cuts)\r
-                       RemoverUtil.remove(graph, cut);\r
-        }\r
-        \r
-        return result;\r
-        \r
-    }\r
-\r
-    @SuppressWarnings("rawtypes")\r
-    @Override\r
-    public Object getAdapter(Class adapter) {\r
-        if(Resource.class == adapter) return resource;\r
-        return null;\r
-    }\r
-\r
-}\r
+/*******************************************************************************
+ * Copyright (c) 2007, 2010 Association for Decentralized Information Management
+ * in Industry THTH ry.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ *     VTT Technical Research Centre of Finland - initial API and implementation
+ *******************************************************************************/
+package org.simantics.db.layer0.adapter.impl;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+import org.simantics.db.ReadGraph;
+import org.simantics.db.Resource;
+import org.simantics.db.WriteGraph;
+import org.simantics.db.common.utils.NameUtils;
+import org.simantics.db.exception.DatabaseException;
+import org.simantics.db.layer0.adapter.PasteHandlerAdapter;
+import org.simantics.db.layer0.internal.SimanticsInternal;
+import org.simantics.db.layer0.util.ClipboardUtils;
+import org.simantics.db.layer0.util.ModelTransferableGraphSource;
+import org.simantics.db.layer0.util.PasteEventHandler;
+import org.simantics.db.layer0.util.RemoverUtil;
+import org.simantics.db.layer0.util.SimanticsClipboard;
+import org.simantics.db.layer0.util.SimanticsClipboard.Representation;
+import org.simantics.db.layer0.util.SimanticsKeys;
+import org.simantics.db.layer0.util.TransferableGraphConfiguration2.SeedSpec;
+import org.simantics.db.layer0.util.TransferableGraphConfiguration2.SeedSpec.SeedSpecType;
+import org.simantics.graph.db.IImportAdvisor;
+import org.simantics.graph.db.IImportAdvisor2;
+import org.simantics.graph.db.IImportAdvisor2.RootInfo;
+import org.simantics.graph.db.TransferableGraphException;
+import org.simantics.graph.db.TransferableGraphSource;
+import org.simantics.graph.db.TransferableGraphs;
+import org.simantics.graph.representation.Identity;
+import org.simantics.graph.representation.Root;
+import org.simantics.graph.representation.TransferableGraph1;
+import org.simantics.graph.representation.TransferableGraphUtils;
+import org.simantics.layer0.Layer0;
+
+public class DefaultPasteHandler extends PasteHandlerAdapter {
+
+    protected Resource resource;
+
+    public DefaultPasteHandler(Resource resource) {
+        this.resource = resource;
+    }
+
+    public static void defaultExecute(TransferableGraph1 tg, Resource resource, IImportAdvisor advisor) throws DatabaseException, TransferableGraphException {
+        TransferableGraphs.importGraph1(SimanticsInternal.getSession(), tg, advisor);
+    }
+
+    public static void defaultExecute(WriteGraph graph, TransferableGraph1 tg, Resource resource, IImportAdvisor advisor) throws DatabaseException {
+        TransferableGraphs.importGraph1(graph, tg, advisor);
+    }
+
+    public void execute(WriteGraph graph, TransferableGraph1 tg, Resource resource, IImportAdvisor advisor) throws DatabaseException {
+       defaultExecute(graph, tg, resource, advisor);
+    }
+
+    /**
+     * Override this in your inherited class if post processing is done.
+     */
+    public void onPasteBegin(WriteGraph graph) throws DatabaseException {
+    }
+
+    /**
+     * Override this in your inherited class if post processing is done
+     * advisor.getTarget() returns an object under which data is copied
+     * advisor.getRoot() returns the object which have been pasted.
+     * @param representations TODO
+     */
+    public void onPaste(WriteGraph graph, IImportAdvisor2 advisor, Set<Representation> representations) throws DatabaseException {
+    }
+
+    /**
+     * Override this in your inherited class if post processing is done.
+     */
+    public void onPasteEnd(WriteGraph graph) throws DatabaseException {
+    }
+    
+    public IImportAdvisor2 getAdvisor(ReadGraph graph, TransferableGraph1 tg, Resource target, PasteEventHandler handler) throws DatabaseException {
+       
+       Collection<Identity> roots = TransferableGraphUtils.getRoots(tg);
+       if(roots.size() == 1) {
+               Root root = (Root)roots.iterator().next().definition;
+               Resource type = graph.getPossibleResource(root.type);
+               ImportAdvisorFactory factory = graph.getPossibleAdapter(type, ImportAdvisorFactory.class);
+               if(factory != null) {
+                       if(handler != null)
+                               return handler.createAdvisor(graph, factory, target);
+                       else
+                               return factory.create(graph, target, Collections.<String,Object>emptyMap());
+               }
+       }
+
+       return new DefaultPasteImportAdvisor(target);
+    }
+
+    public Collection<Resource> pasteObject(WriteGraph graph, Set<Representation> object, PasteEventHandler handler) throws DatabaseException {
+       Collection<Resource> result = new ArrayList<>();
+        TransferableGraphSource tgs = ClipboardUtils.accept(graph, object, SimanticsKeys.KEY_TRANSFERABLE_GRAPH_SOURCE);
+        if (tgs != null) {
+               TransferableGraph1 tg = TransferableGraphs.create(graph, tgs);
+            IImportAdvisor2 advisor = getAdvisor(graph, tg, resource, handler); 
+            execute(graph, tg, resource, advisor);
+            Collection<RootInfo> roots = advisor.getRootInfo();
+            if(handler != null) {
+               for(RootInfo r : roots) handler.postProcess(graph, r.resource);
+            }
+            onPaste(graph, advisor, object);
+            if(tgs instanceof ModelTransferableGraphSource) {
+               
+               ModelTransferableGraphSource mtgs = (ModelTransferableGraphSource)tgs;
+               
+               loop: for(SeedSpec spec : mtgs.getConfiguration().seeds) {
+                       if(SeedSpecType.SPECIAL_ROOT.equals(spec.specType)) continue;
+                       for(RootInfo info : roots) {
+                               if(spec.name.equals(info.root.name)) {
+                                       result.add(info.resource);
+                                       continue loop;
+                               }
+                       }
+                               // Fallback
+                               result.clear();
+                               result.addAll(advisor.getRoots());
+                               break;
+               }
+               
+            } else {
+               result.addAll(advisor.getRoots());
+            }
+        }
+        return result;
+    }
+
+    @Override
+    public Collection<Resource> pasteFromClipboard(WriteGraph graph, SimanticsClipboard clipboard, PasteEventHandler handler) throws DatabaseException {
+        
+       Collection<Resource> result = new ArrayList<>();
+       
+       
+       // Check if root resource is allowed for pasting
+       checkIfRootAllowsPaste(graph);
+       
+       Map<String,Object> hints = Collections.singletonMap(ClipboardUtils.HINT_TARGET_RESOURCE, resource);
+       
+        onPasteBegin(graph);
+
+        final Set<Resource> cuts = new HashSet<>();
+        for(Set<Representation> object : clipboard.getContents()) {
+            Collection<Resource> cut = ClipboardUtils.accept(object, SimanticsKeys.KEY_CUT_RESOURCES);
+            TransferableGraphSource tg = ClipboardUtils.accept(graph, object, SimanticsKeys.KEY_TRANSFERABLE_GRAPH_SOURCE, hints);
+            if(tg != null) {
+               result.addAll(pasteObject(graph, object, handler));
+               if (cut != null)
+                    cuts.addAll(cut);
+            } else {
+               Layer0 L0 = Layer0.getInstance(graph);
+               for(Resource r : cut) {
+                       graph.deny(r, L0.PartOf);
+                       graph.claim(resource, L0.ConsistsOf, L0.PartOf, r);
+                       result.add(r);
+               }
+            }
+        }
+
+        onPasteEnd(graph);
+
+        if(!cuts.isEmpty()) {
+               for (Resource cut : cuts)
+                       RemoverUtil.remove(graph, cut);
+        }
+        
+        return result;
+        
+    }
+
+    protected void checkIfRootAllowsPaste(ReadGraph graph) throws DatabaseException {
+        Layer0 L0 = Layer0.getInstance(graph);
+        // check if root is published
+        Boolean published = graph.getPossibleRelatedValue(resource, L0.Entity_published);
+        if (published != null && published) {
+            throw new DatabaseException("Target resource " + NameUtils.getSafeName(graph, resource) + " is published and does not allow paste.");
+        }
+    }
+
+    @SuppressWarnings("rawtypes")
+    @Override
+    public Object getAdapter(Class adapter) {
+        if(Resource.class == adapter) return resource;
+        return null;
+    }
+
+}