]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.document.ui/src/org/simantics/document/ui/graphfile/DocumentVersionUtils.java
Migrated source code from Simantics SVN
[simantics/platform.git] / bundles / org.simantics.document.ui / src / org / simantics / document / ui / graphfile / DocumentVersionUtils.java
1 package org.simantics.document.ui.graphfile;\r
2 \r
3 import org.simantics.db.ReadGraph;\r
4 import org.simantics.db.Resource;\r
5 import org.simantics.db.WriteGraph;\r
6 import org.simantics.db.common.utils.NameUtils;\r
7 import org.simantics.db.exception.DatabaseException;\r
8 import org.simantics.document.DocumentResource;\r
9 import org.simantics.layer0.Layer0;\r
10 /**\r
11  * Util class for managing document versions\r
12  * \r
13  * Document version history mode  is searched with relations:\r
14  * 1. l0.PartOf\r
15  * 2. l0.IsOwnedBy\r
16  * 3. l0.IsDependencyOf \r
17  * \r
18  * If library is not found, history mode is assumed to be flat.\r
19  * \r
20  * In order to have working tree history, the library must contain proper configuration for relations:\r
21  *  doc.HasLibraryRelation\r
22  *  doc.HasVersionType\r
23  *  \r
24  * @author Marko Luukkainen <marko.luukkainen@vtt.fi>\r
25  *\r
26  */\r
27 public class DocumentVersionUtils {\r
28 \r
29         public enum VersionMode{FLAT,TREE};\r
30         \r
31         \r
32         /**\r
33          * Adds a new document version.\r
34          * \r
35          * Expects that newDocument is not part of document version chain, and oldDocument does not have newer version.\r
36          * \r
37          * @param graph\r
38          * @param oldDocument\r
39          * @param newDocument\r
40          * @param relation\r
41          * @throws DatabaseException\r
42          */\r
43         public static void createNewVersion(WriteGraph graph, Resource oldDocument, Resource newDocument, Resource relation) throws DatabaseException{\r
44                 DocumentResource doc = DocumentResource.getInstance(graph);\r
45                 if (graph.hasStatement(oldDocument, doc.HasNewerVersion))\r
46                         throw new DatabaseException("Document " + NameUtils.getSafeName(graph, oldDocument) +" has already new version");\r
47                 \r
48                 Resource inverse = graph.getInverse(relation);\r
49                 Resource lib = graph.getSingleObject(oldDocument, inverse);\r
50                 String modeString = graph.getPossibleRelatedValue(lib, doc.HasVersionType);\r
51                 VersionMode mode = VersionMode.FLAT;\r
52                 if (modeString != null)\r
53                         mode = VersionMode.valueOf(modeString);\r
54                 \r
55                 graph.claim(oldDocument, doc.HasNewerVersion, newDocument);\r
56                 graph.claim(lib, relation, newDocument);\r
57                 \r
58                 if (mode == VersionMode.TREE) {\r
59                         graph.deny(lib,relation,oldDocument);\r
60                         graph.claim(newDocument,relation,oldDocument);\r
61                 }\r
62                 FileDocumentUtil.createUniqueName(graph, newDocument);\r
63         }\r
64         \r
65         /**\r
66          * Sets document version relationship between two documents. \r
67          * \r
68          * If the documents are already part of the same version chain this method does nothing.\r
69          * \r
70          * If documents are already set to some version chain with given relation, this method replaces the exiting links.\r
71          * \r
72          * @param graph\r
73          * @param document1\r
74          * @param document2\r
75          * @param versionRel\r
76          * @throws DatabaseException\r
77          */\r
78         public static void setVersion(WriteGraph graph, Resource document1, Resource document2, Resource versionRel) throws DatabaseException {\r
79                 DocumentResource doc = DocumentResource.getInstance(graph);\r
80                 // document type must match\r
81                 if (!graph.getSingleType(document2, doc.Document).equals(graph.getSingleType(document1, doc.Document)))\r
82                         return;\r
83                 if (!versionRel.equals(doc.HasNewerVersion) && !(versionRel.equals(doc.HasOlderVersion)))\r
84                         throw new IllegalArgumentException("Unknow version relation + " + graph.getPossibleURI(versionRel));\r
85                 \r
86                 Resource versionRelInv = graph.getInverse(versionRel);\r
87                 // toSet must not be part of the document's version history\r
88                 Resource r = document1;\r
89                 while (r != null) {\r
90                         if (r.equals(document2))\r
91                                 return;\r
92                         r = graph.getPossibleObject(r, versionRel);\r
93                 }\r
94                 \r
95                 r = document2;\r
96                 while (r != null) {\r
97                         if (r.equals(document1))\r
98                                 return;\r
99                         r = graph.getPossibleObject(r, versionRel);\r
100                 }\r
101                 // At the moment document revision history is linear (no branching).\r
102                 Resource document1Ver = graph.getPossibleObject(document1, versionRel);\r
103                 if (document1Ver != null)\r
104                         unsetVersion(graph, document1, document1Ver, versionRel);\r
105                 Resource document2Ver = graph.getPossibleObject(document2, versionRelInv);\r
106                 if (document2Ver != null)\r
107                         unsetVersion(graph, document2, document2Ver, versionRelInv);\r
108                 \r
109                 graph.claim(document1, versionRel, document2);\r
110                 \r
111                 Resource lib = getLib(graph, document1);\r
112                 if (lib != null) {\r
113                         Resource relation = graph.getPossibleObject(lib, doc.HasLibraryRelation);\r
114                         String type= graph.getPossibleRelatedValue(lib, doc.HasVersionType);\r
115                         if ("TREE".equals(type) && relation != null) {\r
116                                 if (versionRel.equals(doc.HasOlderVersion)) {\r
117                                         graph.deny(document2, graph.getInverse(relation));\r
118                                         graph.claim(document1,relation,document2);\r
119                                 } else {\r
120                                         graph.deny(document1, graph.getInverse(relation));\r
121                                         graph.claim(document2,relation,document1);\r
122                                 }\r
123                         }\r
124                         \r
125                 }\r
126         }\r
127         \r
128         /**\r
129          * Unlinks document version relationship between two documents. \r
130          * @param graph\r
131          * @param document1\r
132          * @param document2\r
133          * @param versionRel\r
134          * @throws DatabaseException\r
135          */\r
136         public static void unsetVersion(WriteGraph graph, Resource document1, Resource document2, Resource versionRel) throws DatabaseException {\r
137                 DocumentResource doc = DocumentResource.getInstance(graph);\r
138                 if (!versionRel.equals(doc.HasNewerVersion) && !(versionRel.equals(doc.HasOlderVersion)))\r
139                         throw new IllegalArgumentException("Unknow version relation + " + graph.getPossibleURI(versionRel));\r
140                 \r
141                 graph.deny(document1, versionRel,document2);\r
142                 Resource lib = getLib(graph, document1);\r
143                 if (lib != null) {\r
144                         Resource relation = graph.getPossibleObject(lib, doc.HasLibraryRelation);\r
145                         String type= graph.getPossibleRelatedValue(lib, doc.HasVersionType);\r
146                         if ("TREE".equals(type) && relation != null) {\r
147                                 if (versionRel.equals(doc.HasOlderVersion)) {\r
148                                         graph.deny(document1, relation);\r
149                                         graph.claim(lib,relation,document2);\r
150                                         FileDocumentUtil.createUniqueName(graph, document2);\r
151                                 } else {\r
152                                         graph.deny(document1, graph.getInverse(relation));\r
153                                         graph.claim(lib,relation,document1);\r
154                                         FileDocumentUtil.createUniqueName(graph, document1);\r
155                                 }\r
156                         }\r
157                         \r
158                 }\r
159         }\r
160         \r
161         private static Resource getLib(ReadGraph graph, Resource document) throws DatabaseException {\r
162                 Layer0 l0 = Layer0.getInstance(graph);\r
163                 DocumentResource doc = DocumentResource.getInstance(graph);\r
164                 Resource r = document;\r
165                 while (true) {\r
166                         Resource lib = graph.getPossibleObject(r, l0.PartOf);\r
167                         if (lib == null)\r
168                                 lib = graph.getPossibleObject(r, l0.IsOwnedBy);\r
169                         if (lib == null)\r
170                                 lib =  graph.getPossibleObject(r, l0.IsDependencyOf);\r
171                         if (lib == null)\r
172                                 return null;\r
173                         if (!graph.isInstanceOf(lib, doc.Document))\r
174                                 return lib;\r
175                         r = lib;\r
176                 }\r
177         }\r
178 }\r