1 package org.simantics.document;
3 import org.simantics.db.ReadGraph;
4 import org.simantics.db.Resource;
5 import org.simantics.db.WriteGraph;
6 import org.simantics.db.common.utils.NameUtils;
7 import org.simantics.db.exception.DatabaseException;
8 import org.simantics.document.DocumentResource;
9 import org.simantics.layer0.Layer0;
11 * Util class for managing document versions
13 * Document version history mode is searched with relations:
16 * 3. l0.IsDependencyOf
18 * If library is not found, history mode is assumed to be flat.
20 * In order to have working tree history, the library must contain proper configuration for relations:
21 * doc.HasLibraryRelation
24 * @author Marko Luukkainen <marko.luukkainen@vtt.fi>
27 public class DocumentVersionUtils {
29 public enum VersionMode{FLAT,TREE};
33 * Adds a new document version.
35 * Expects that newDocument is not part of document version chain, and oldDocument does not have newer version.
41 * @throws DatabaseException
43 public static void createNewVersion(WriteGraph graph, Resource oldDocument, Resource newDocument, Resource relation) throws DatabaseException{
44 DocumentResource doc = DocumentResource.getInstance(graph);
45 if (graph.hasStatement(oldDocument, doc.HasNewerVersion))
46 throw new DatabaseException("Document " + NameUtils.getSafeName(graph, oldDocument) +" has already new version");
48 Resource inverse = graph.getInverse(relation);
49 Resource lib = graph.getSingleObject(oldDocument, inverse);
50 String modeString = graph.getPossibleRelatedValue(lib, doc.HasVersionType);
51 VersionMode mode = VersionMode.FLAT;
52 if (modeString != null)
53 mode = VersionMode.valueOf(modeString);
55 graph.claim(oldDocument, doc.HasNewerVersion, newDocument);
56 graph.claim(lib, relation, newDocument);
58 if (mode == VersionMode.TREE) {
59 graph.deny(lib,relation,oldDocument);
60 graph.claim(newDocument,relation,oldDocument);
62 FileDocumentUtil.createUniqueName(graph, newDocument);
66 * Sets document version relationship between two documents.
68 * If the documents are already part of the same version chain this method does nothing.
70 * If documents are already set to some version chain with given relation, this method replaces the exiting links.
76 * @throws DatabaseException
78 public static void setVersion(WriteGraph graph, Resource document1, Resource document2, Resource versionRel) throws DatabaseException {
79 DocumentResource doc = DocumentResource.getInstance(graph);
80 // document type must match
81 if (!graph.getSingleType(document2, doc.Document).equals(graph.getSingleType(document1, doc.Document)))
83 if (!versionRel.equals(doc.HasNewerVersion) && !(versionRel.equals(doc.HasOlderVersion)))
84 throw new IllegalArgumentException("Unknow version relation + " + graph.getPossibleURI(versionRel));
86 Resource versionRelInv = graph.getInverse(versionRel);
87 // toSet must not be part of the document's version history
88 Resource r = document1;
90 if (r.equals(document2))
92 r = graph.getPossibleObject(r, versionRel);
97 if (r.equals(document1))
99 r = graph.getPossibleObject(r, versionRel);
101 // At the moment document revision history is linear (no branching).
102 Resource document1Ver = graph.getPossibleObject(document1, versionRel);
103 if (document1Ver != null)
104 unsetVersion(graph, document1, document1Ver, versionRel);
105 Resource document2Ver = graph.getPossibleObject(document2, versionRelInv);
106 if (document2Ver != null)
107 unsetVersion(graph, document2, document2Ver, versionRelInv);
109 graph.claim(document1, versionRel, document2);
111 Resource lib = getLib(graph, document1);
113 Resource relation = graph.getPossibleObject(lib, doc.HasLibraryRelation);
114 String type= graph.getPossibleRelatedValue(lib, doc.HasVersionType);
115 if ("TREE".equals(type) && relation != null) {
116 if (versionRel.equals(doc.HasOlderVersion)) {
117 graph.deny(document2, graph.getInverse(relation));
118 graph.claim(document1,relation,document2);
120 graph.deny(document1, graph.getInverse(relation));
121 graph.claim(document2,relation,document1);
129 * Unlinks document version relationship between two documents.
134 * @throws DatabaseException
136 public static void unsetVersion(WriteGraph graph, Resource document1, Resource document2, Resource versionRel) throws DatabaseException {
137 DocumentResource doc = DocumentResource.getInstance(graph);
138 if (!versionRel.equals(doc.HasNewerVersion) && !(versionRel.equals(doc.HasOlderVersion)))
139 throw new IllegalArgumentException("Unknow version relation + " + graph.getPossibleURI(versionRel));
141 graph.deny(document1, versionRel,document2);
142 Resource lib = getLib(graph, document1);
144 Resource relation = graph.getPossibleObject(lib, doc.HasLibraryRelation);
145 String type= graph.getPossibleRelatedValue(lib, doc.HasVersionType);
146 if ("TREE".equals(type) && relation != null) {
147 if (versionRel.equals(doc.HasOlderVersion)) {
148 graph.deny(document1, relation);
149 graph.claim(lib,relation,document2);
150 FileDocumentUtil.createUniqueName(graph, document2);
152 graph.deny(document1, graph.getInverse(relation));
153 graph.claim(lib,relation,document1);
154 FileDocumentUtil.createUniqueName(graph, document1);
161 private static Resource getLib(ReadGraph graph, Resource document) throws DatabaseException {
162 Layer0 l0 = Layer0.getInstance(graph);
163 DocumentResource doc = DocumentResource.getInstance(graph);
164 Resource r = document;
166 Resource lib = graph.getPossibleObject(r, l0.PartOf);
168 lib = graph.getPossibleObject(r, l0.IsOwnedBy);
170 lib = graph.getPossibleObject(r, l0.IsDependencyOf);
173 if (!graph.isInstanceOf(lib, doc.Document))