package org.simantics.db.layer0.util; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.Map; import java.util.TreeMap; import org.simantics.databoard.binding.mutable.Variant; import org.simantics.db.ReadGraph; import org.simantics.db.RequestProcessor; import org.simantics.db.Resource; import org.simantics.db.Statement; import org.simantics.db.common.NamedResource; import org.simantics.db.common.request.UniqueRead; import org.simantics.db.exception.DatabaseException; import org.simantics.db.layer0.adapter.SubgraphExtent.ExtentStatus; import org.simantics.db.layer0.util.DomainProcessor3.ExclusionDecision; import org.simantics.db.layer0.util.TransferableGraphConfiguration2.SeedSpec.SeedSpecType; import org.simantics.scl.runtime.function.Function1; public class TransferableGraphConfiguration2 { public static class SeedSpec { public static enum SeedSpecType { INTERNAL, ROOT, SPECIAL_ROOT } public final Resource resource; public final String name; // Special roots are not normal seeds - e.g. %model public final SeedSpecType specType; /** * Optional, may be null. */ public final String type; public SeedSpec(Resource resource, String name, SeedSpecType specType) { this(resource, name, specType, null); } public SeedSpec(Resource resource, String name, SeedSpecType specType, String type) { if (resource == null) throw new NullPointerException("null resource"); if (name == null) throw new NullPointerException("null name"); this.resource = resource; this.name = name; this.specType = specType; this.type = type; } public static SeedSpec internal(Resource resource) { return new SeedSpec(resource, "", SeedSpecType.ROOT); } @Override public String toString() { return "SeedSpec[" + name + ", " + resource + ", " + specType + ", " + type + "]"; } @Override public int hashCode() { final int prime = 31; int result = 1; result = prime * result + specType.hashCode(); result = prime * result + resource.hashCode(); result = prime * result + name.hashCode(); result = prime * result + (type != null ? type.hashCode() : 0); return result; } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (getClass() != obj.getClass()) return false; SeedSpec other = (SeedSpec) obj; return specType.equals(other.specType) && resource.equals(other.resource) && name.equals(other.name) && objectEquals(type, other.type); } private boolean objectEquals(Object o1, Object o2) { if (o1 == o2) return true; if (o1 == null && o2 == null) return true; if (o1 == null || o2 == null) return false; return o1.equals(o2); } } final public TreeMap baseExtensions = new TreeMap<>(); final public Resource indexRoot; final public Collection seeds; final public Map preStatus; final public boolean ignoreVirtualResources; final public boolean validate; /** * true to export values, false to skip the actual * values and only write the resource id. */ public boolean values = true; public Collection valueModifiers; public Function1 exclusionFunction; public TransferableGraphConfiguration2(Resource indexRoot, Collection seeds, Map preStatus, boolean ignoreVirtualResources, boolean validate) { this.indexRoot = indexRoot; this.seeds = seeds; this.preStatus = preStatus; this.ignoreVirtualResources = ignoreVirtualResources; this.validate = validate; this.valueModifiers = null; } public TransferableGraphConfiguration2(Resource indexRoot, Collection roots, Map preStatus, boolean ignoreVirtualResources) { this(indexRoot, roots, preStatus, ignoreVirtualResources, true); } public TransferableGraphConfiguration2(Resource indexRoot, Collection roots, Map preStatus) { this(indexRoot, roots, preStatus, true); } public TransferableGraphConfiguration2(TransferableGraphConfiguration2 conf) throws DatabaseException { this(conf.indexRoot, conf.seeds, conf.preStatus, conf.ignoreVirtualResources, conf.validate); } public TransferableGraphConfiguration2(ReadGraph graph, Resource model, boolean ignoreVirtualResources, boolean validate) throws DatabaseException { this(new TGConfigurer(graph, ignoreVirtualResources, validate).roots2(Collections.singletonList(model)).create()); } public TransferableGraphConfiguration2(ReadGraph graph, Collection roots, boolean ignoreVirtualResources, boolean validate) throws DatabaseException { this(new TGConfigurer(graph, ignoreVirtualResources, validate).roots2(roots).create()); } public TransferableGraphConfiguration2(ReadGraph graph, Resource model, boolean ignoreVirtualResources) throws DatabaseException { this(graph, model, ignoreVirtualResources, true); } public TransferableGraphConfiguration2(ReadGraph graph, Resource model) throws DatabaseException { this(graph, model, true); } public TransferableGraphConfiguration2(ReadGraph graph, Collection roots, Collection resourceRoots, Collection exclusions) throws DatabaseException { this(new TGConfigurer(graph, true).roots(roots).roots2(resourceRoots).exclusions(exclusions).create()); } public TransferableGraphConfiguration2(ReadGraph graph, Collection roots, Collection resourceRoots, Collection exclusions, boolean ignoreVirtualResource, boolean validate) throws DatabaseException { this(new TGConfigurer(graph, ignoreVirtualResource, validate).roots(roots).roots2(resourceRoots).exclusions(exclusions).create()); } public static TransferableGraphConfiguration2 createWithNames(RequestProcessor processor, final Collection roots, final Collection exclusions, final boolean ignoreVirtualResource, final boolean validate) throws DatabaseException { return processor.sync(new UniqueRead() { @Override public TransferableGraphConfiguration2 perform(ReadGraph graph) throws DatabaseException { return new TransferableGraphConfiguration2(graph, translate(roots), Collections.emptyList(), exclusions, ignoreVirtualResource, validate); } }); } public static TransferableGraphConfiguration2 createWithNames2(RequestProcessor processor, final Collection roots, final Collection exclusions, final boolean ignoreVirtualResource, final boolean validate) throws DatabaseException { return processor.sync(new UniqueRead() { @Override public TransferableGraphConfiguration2 perform(ReadGraph graph) throws DatabaseException { return new TransferableGraphConfiguration2(graph, roots, Collections.emptyList(), exclusions, ignoreVirtualResource, validate); } }); } public static TransferableGraphConfiguration2 createWithNames(RequestProcessor processor, final Collection roots, final Collection exclusions) throws DatabaseException { return createWithNames(processor, roots, exclusions, true, true); } public static TransferableGraphConfiguration2 createWithResources(RequestProcessor processor, final Collection roots, final Collection exclusions) throws DatabaseException { return processor.sync(new UniqueRead() { @Override public TransferableGraphConfiguration2 perform(ReadGraph graph) throws DatabaseException { return new TransferableGraphConfiguration2(graph, Collections.emptyList(), roots, exclusions); } }); } public static TransferableGraphConfiguration2 createForModel(RequestProcessor processor, final Resource model) throws DatabaseException { return createWithResources(processor, Collections.singletonList(model), Collections.emptyList()); } private static Collection translate(Collection roots) { ArrayList result = new ArrayList<>(); for(NamedResource nr : roots) result.add(new SeedSpec(nr.getResource(), nr.getName(), SeedSpecType.ROOT)); return result; } }