package org.simantics.db.layer0.genericrelation; import java.io.IOException; import java.util.ArrayList; import java.util.Map; import java.util.TreeMap; import org.simantics.databoard.Databoard; import org.simantics.databoard.annotations.Arguments; import org.simantics.databoard.annotations.Union; import org.simantics.databoard.binding.Binding; import org.simantics.databoard.binding.error.BindingConstructionException; import org.simantics.databoard.serialization.SerializationException; import org.simantics.databoard.serialization.Serializer; import org.simantics.databoard.serialization.SerializerConstructionException; import org.simantics.db.Metadata; import org.simantics.db.ReadGraph; import org.simantics.db.Resource; import org.simantics.db.Session; import org.simantics.db.common.utils.NameUtils; import org.simantics.db.exception.DatabaseException; import org.simantics.layer0.Layer0; public class DependencyChanges implements Metadata { public final @Arguments({Resource.class, Change[].class}) TreeMap modelChanges; public final boolean hasUnresolved; public DependencyChanges(TreeMap modelChanges, boolean hasUnresolved) { this.modelChanges = modelChanges; this.hasUnresolved = hasUnresolved; } public DependencyChanges(Map> _modelChanges, boolean hasUnresolved) { this(new TreeMap(), hasUnresolved); for(Map.Entry> entry : _modelChanges.entrySet()) { ArrayList value = entry.getValue(); modelChanges.put(entry.getKey(), value.toArray(new Change[value.size()])); } } public static enum ChangeType { LINK_CHANGE, COMPONENT_ADDITION, COMPONENT_REMOVAL, COMPONENT_MODIFICATION } @Union({LinkChange.class, ComponentAddition.class, ComponentRemoval.class, ComponentModification.class}) public static interface Change { ChangeType getType(); String toString(ReadGraph graph) throws DatabaseException; } public static class LinkChange implements Change { public final Resource component; public LinkChange(Resource component) { this.component = component; } @Override public ChangeType getType() { return ChangeType.LINK_CHANGE; } @Override public String toString(ReadGraph graph) throws DatabaseException { return "LinkChange[" + NameUtils.getSafeName(graph, component, true) + "]"; } } public static class ComponentAddition implements Change { public final Resource component; public final Resource parent; public ComponentAddition(Resource component, Resource parent) { this.component = component; this.parent = parent; } @Override public ChangeType getType() { return ChangeType.COMPONENT_ADDITION; } @Override public String toString() { return "ComponentAddition[" + component + "]"; } public boolean isValid(ReadGraph graph) throws DatabaseException { return graph.hasStatement(component, Layer0.getInstance(graph).PartOf, parent); } @Override public String toString(ReadGraph graph) throws DatabaseException { return "ComponentAddition[" + NameUtils.getSafeName(graph, component, true) + "]"; } } public static class ComponentRemoval implements Change { public final Resource component; public final Resource parent; public ComponentRemoval(Resource component, Resource parent) { this.component = component; this.parent = parent; } @Override public ChangeType getType() { return ChangeType.COMPONENT_REMOVAL; } public boolean isValid(ReadGraph graph) throws DatabaseException { return !graph.hasStatement(component, Layer0.getInstance(graph).PartOf, parent); } @Override public String toString(ReadGraph graph) throws DatabaseException { return "ComponentRemoval[component=" + NameUtils.getSafeName(graph, component, true) + ", parent=" + NameUtils.getSafeName(graph, parent, true) + "]"; } } public static class ComponentModification implements Change { public final Resource component; public ComponentModification(Resource component) { this.component = component; } @Override public ChangeType getType() { return ChangeType.COMPONENT_MODIFICATION; } @Override public String toString(ReadGraph graph) throws DatabaseException { return "ComponentModification[" + NameUtils.getSafeName(graph, component, true) + "]"; } } public Change[] get(Resource model) { return modelChanges.get(model); } public Map get() { return modelChanges; } @Override public byte[] serialise(Session session) { try { Databoard databoard = session.getService( Databoard.class ); Binding binding = databoard.getBinding( DependencyChanges.class ); Serializer serializer = databoard.getSerializer( binding ); return serializer.serialize(this); } catch (SerializationException e) { e.printStackTrace(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (SerializerConstructionException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (BindingConstructionException e) { // TODO Auto-generated catch block e.printStackTrace(); } return new byte[0]; } public static DependencyChanges deserialise(Session session, byte[] input) { try { Databoard databoard = session.getService( Databoard.class ); Binding binding = databoard.getBinding( DependencyChanges.class ); Serializer serializer = databoard.getSerializer( binding ); return (DependencyChanges) serializer.deserialize(input); } catch (SerializationException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } catch (SerializerConstructionException e) { e.printStackTrace(); } catch (BindingConstructionException e) { e.printStackTrace(); } return null; } public boolean isEmpty() { return modelChanges.isEmpty() && !hasUnresolved; } }