package org.simantics.modeling.utils; import java.io.File; import java.io.IOException; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; import java.util.TreeMap; import org.simantics.databoard.Bindings; import org.simantics.db.ReadGraph; import org.simantics.db.Resource; import org.simantics.db.common.NamedResource; import org.simantics.db.common.utils.CommonDBUtils; import org.simantics.db.common.utils.NameUtils; import org.simantics.db.exception.DatabaseException; import org.simantics.db.layer0.variable.Variable; import org.simantics.db.layer0.variable.Variables; import org.simantics.graphfile.ontology.GraphFileResource; import org.simantics.layer0.Layer0; import org.simantics.structural.stubs.StructuralResource2; import org.simantics.structural2.variables.Connection; import org.simantics.structural2.variables.VariableConnectionPointDescriptor; import org.simantics.utils.FileUtils; public class DumpOntologyStructure { private Resource ontology; private Set containers = new HashSet<>(); private Set folders = new HashSet<>(); private Map names = new HashMap<>(); private Map parents = new HashMap<>(); private Map libraryFolders = new HashMap<>(); private Set modules = new HashSet<>(); private Map moduleCodes = new HashMap<>(); private Set pgraphs = new HashSet<>(); private Map pgraphCodes = new HashMap<>(); private Set graphFiles = new HashSet<>(); private Map graphFileBytes = new HashMap<>(); private Set componentTypes = new HashSet<>(); private Map componentTypeDumps = new HashMap<>(); private Set components = new HashSet<>(); private Map componentDumps = new HashMap<>(); private void readNameAndParent(ReadGraph graph, Resource container, Resource r) throws DatabaseException { parents.put(r, container); names.put(r, NameUtils.getSafeName(graph, r)); } private void readLibraries(ReadGraph graph, Resource container) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, L0.Library)) { folders.add(r); names.put(r, NameUtils.getSafeName(graph, r)); parents.put(r, container); readNameAndParent(graph, container, r); readLibraries(graph, r); } containers.addAll(folders); } private void readComponentTypes(ReadGraph graph) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); StructuralResource2 STR = StructuralResource2.getInstance(graph); for(Resource container : containers) { for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, STR.ComponentType)) { folders.add(r); componentTypes.add(r); readNameAndParent(graph, container, r); ComponentTypePropertiesResult data = graph.syncRequest(new HeadlessComponentTypePropertiesResultRequest(r)); StringBuilder dump = new StringBuilder(); for(ComponentTypeViewerPropertyInfo pi : data.getProperties()) { dump.append(pi.name); dump.append(" "); dump.append(pi.type); dump.append(" "); dump.append(pi.defaultValue); if(pi.unit != null) { dump.append(" "); dump.append(pi.unit); } dump.append(" "); dump.append(pi.label); if(pi.description != null) { dump.append(" "); dump.append(pi.description); } dump.append("\n"); } for(NamedResource nr : data.getConnectionPoints()) { dump.append("cp "); dump.append(nr.getName()); dump.append("\n"); } componentTypeDumps.put(r, dump.toString()); } } containers.addAll(folders); } private void readComposites(ReadGraph graph) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); StructuralResource2 STR = StructuralResource2.getInstance(graph); for(Resource container : containers) { for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, STR.Composite)) { folders.add(r); readNameAndParent(graph, container, r); } } containers.addAll(folders); } private void readComponents(ReadGraph graph) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); StructuralResource2 STR = StructuralResource2.getInstance(graph); for(Resource container : containers) { for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, STR.Component)) { if(folders.contains(r)) continue; components.add(r); readNameAndParent(graph, container, r); Variable v = Variables.getVariable(graph, r); TreeMap properties = new TreeMap<>(); for(Variable property : v.getProperties(graph)) properties.put(property.getName(graph), property); StringBuilder dump = new StringBuilder(); for(Variable property : properties.values()) { String possibleValue = property.getPossiblePropertyValue(graph, "HasDisplayValue", Bindings.STRING); if(possibleValue != null) { dump.append(property.getName(graph)); dump.append(" "); dump.append(possibleValue); dump.append("\n"); } if(property.getClassifications(graph).contains(StructuralResource2.URIs.ConnectionRelation)) { dump.append(property.getName(graph)); Connection c = property.getValue(graph); for(VariableConnectionPointDescriptor desc : c.getConnectionPointDescriptors(graph, null)) { dump.append(" "); dump.append(desc.getRelativeRVI(graph, v)); } dump.append("\n"); } } componentDumps.put(r, dump.toString()); } } } private void readSCLModules(ReadGraph graph) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); for(Resource container : containers) { for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, L0.SCLModule)) { String code = graph.getPossibleRelatedValue(r, L0.SCLModule_definition, Bindings.STRING); if(code != null) { moduleCodes.put(r, code); } modules.add(r); readNameAndParent(graph, container, r); } } } private void readPGraphs(ReadGraph graph) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); for(Resource container : containers) { for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, L0.PGraph)) { String code = graph.getPossibleRelatedValue(r, L0.PGraph_definition, Bindings.STRING); if(code != null) { pgraphCodes.put(r, code); } pgraphs.add(r); readNameAndParent(graph, container, r); } } } private void readGraphFiles(ReadGraph graph) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); GraphFileResource GF = GraphFileResource.getInstance(graph); for(Resource container : containers) { for(Resource r : CommonDBUtils.objectsWithType(graph, container, L0.ConsistsOf, GF.File)) { byte[] bytes = graph.getPossibleRelatedValue(r, GF.HasFiledata, Bindings.BYTE_ARRAY); if(bytes != null) { graphFileBytes.put(r, bytes); } graphFiles.add(r); readNameAndParent(graph, container, r); } } } public void read(ReadGraph graph, Resource ontology) throws DatabaseException { this.ontology = ontology; containers.add(ontology); readLibraries(graph, ontology); readComponentTypes(graph); readComposites(graph); readComponents(graph); readSCLModules(graph); readPGraphs(graph); readGraphFiles(graph); } private File escapeFile(File file) { if(file.exists()) return file; return new File(escapeFile(file.getParentFile()), FileUtils.escapeFileName(file.getName())); } public void write(File unsafeFolder) throws IOException { File folder = escapeFile(unsafeFolder); if(folder.exists()) FileUtils.deleteAll(folder); folder.mkdirs(); writeLibraries(folder); writeSCLModules(folder); writePGraphs(folder); writeGraphFiles(folder); writeComponentTypes(folder); writeComponents(folder); } private File getFolder(File root, Resource library) { if(ontology.equals(library)) return root; Resource parent = parents.get(library); File parentFolder = getFolder(root, parent); return new File(parentFolder, FileUtils.escapeFileName(names.get(library))); } private File getParentFolder(File root, Resource r) { Resource parent = parents.get(r); return getFolder(root, parent); } private File getFile(File root, Resource r) { return new File(getParentFolder(root, r), FileUtils.escapeFileName(names.get(r))); } private void writeLibraries(File rootFolder) { for(Resource library : folders) { File folder = getFolder(rootFolder, library); folder.mkdirs(); libraryFolders.put(library, folder); } } private void writeSCLModules(File rootFolder) throws IOException { for(Resource r : modules) { FileUtils.writeFile(getFile(rootFolder, r), moduleCodes.get(r).getBytes()); } } private void writePGraphs(File rootFolder) throws IOException { for(Resource r : pgraphs) { FileUtils.writeFile(getFile(rootFolder, r), pgraphCodes.get(r).getBytes()); } } private void writeGraphFiles(File rootFolder) throws IOException { for(Resource r : graphFiles) { FileUtils.writeFile(getFile(rootFolder, r), graphFileBytes.get(r)); } } private void writeComponentTypes(File rootFolder) throws IOException { for(Resource r : componentTypes) { File folder = getFolder(rootFolder, r); File file = new File(folder, "__interface__"); FileUtils.writeFile(file, componentTypeDumps.get(r).getBytes()); } } private void writeComponents(File rootFolder) throws IOException { for(Resource r : components) { FileUtils.writeFile(getFile(rootFolder, r), componentDumps.get(r).getBytes()); } } }