]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.db.layer0/src/org/simantics/db/layer0/variable/VariableUtils.java
Possible variable browse without URI
[simantics/platform.git] / bundles / org.simantics.db.layer0 / src / org / simantics / db / layer0 / variable / VariableUtils.java
1 package org.simantics.db.layer0.variable;
2
3 import java.util.Map;
4
5 import org.simantics.databoard.Bindings;
6 import org.simantics.databoard.adapter.AdaptException;
7 import org.simantics.databoard.adapter.Adapter;
8 import org.simantics.databoard.adapter.AdapterConstructionException;
9 import org.simantics.databoard.binding.Binding;
10 import org.simantics.databoard.type.Datatype;
11 import org.simantics.db.Resource;
12 import org.simantics.db.Statement;
13 import org.simantics.db.WriteGraph;
14 import org.simantics.db.common.request.EnumerationMap;
15 import org.simantics.db.common.request.IsEnumeratedValue;
16 import org.simantics.db.common.utils.CommonDBUtils;
17 import org.simantics.db.exception.DatabaseException;
18 import org.simantics.db.exception.RuntimeDatabaseException;
19 import org.simantics.db.layer0.util.Layer0Utils;
20 import org.simantics.layer0.Layer0;
21 import org.simantics.scl.runtime.function.Function4;
22 import org.simantics.scl.runtime.function.FunctionImpl4;
23
24 public class VariableUtils {
25
26         final private static Binding datatype_binding = Bindings.getBindingUnchecked(Datatype.class);
27         
28         public static Function4<WriteGraph, Variable, Object, Object, String> defaultInputModifier = new FunctionImpl4<WriteGraph, Variable, Object, Object, String>() {
29
30                 public String apply(WriteGraph graph, Variable variable, Object value, Object _binding) {
31                         try {
32                                 return safeApply(graph, variable, value, _binding);
33                         } catch (DatabaseException e) {
34                                 throw new RuntimeDatabaseException(e);
35                         }
36                 }
37
38                 public String safeApply(WriteGraph graph, Variable variable, Object value, Object _binding) throws DatabaseException {
39
40                 Binding binding = (Binding)_binding;
41                 
42                         Variable parent = variable.getParent(graph);
43                         Resource property = variable.getPossiblePredicateResource(graph);
44                         Resource container = parent.getPossibleRepresents(graph);
45                         if(container == null) return null;
46                         if(property == null) return null;
47
48                         CommonDBUtils.selectClusterSet(graph, container);
49
50                         Statement object = graph.getPossibleStatement(container, property);
51                         if(object == null) return null;
52
53                         Resource objectResource = object.getObject();
54                         if(graph.sync(new IsEnumeratedValue(objectResource))) {
55
56                                 Layer0 L0 = Layer0.getInstance(graph);
57                                 Resource type = graph.getSingleObject(objectResource, L0.PartOf);
58                                 
59                                 Map<String, Resource> enumMap = graph.syncRequest(new EnumerationMap(type));
60                                 Resource newLiteral = enumMap.get(value);
61                                 graph.deny(container, property, objectResource);
62                                 graph.claim(container, property, newLiteral);
63                                 
64                                 return null;
65                                 
66                         }
67
68                         Layer0 L0 = Layer0.getInstance(graph);
69                         Statement dt = graph.getPossibleStatement(objectResource, L0.HasDataType);
70                         if (dt == null) {
71                                 throw new DatabaseException("Can't write variable " + variable.getURI(graph) + " since its literal resource " + objectResource + " does not contain a datatype statement"); 
72                         }
73
74                         boolean needsCustomDatatype = !dt.isAsserted(objectResource);
75                         Datatype correctDatatype = graph.getValue(dt.getObject(), datatype_binding);
76                         Binding correctBinding = Bindings.getBinding(correctDatatype);
77
78                         try {
79                                 Adapter adapter = Bindings.getTypeAdapter(binding, correctBinding);
80                                 Object correctValue = adapter.adapt(value);
81                                 if (correctValue == value) {
82                                         // Adapter is passthrough, i.e. the specified binding can be
83                                         // considered correct for the value.
84                                         correctBinding = binding;
85                                 }
86                                 value = correctValue;
87                         } catch (AdapterConstructionException e) {
88                                 throw new DatabaseException("Can't adapt values from source datatype '" + binding.type().toSingleLineString() + "' to target '" + correctDatatype.toSingleLineString() + "'");
89                         } catch (AdaptException e) {
90                                 throw new DatabaseException("Can't adapt value " + value + " from source datatype '" + binding.type().toSingleLineString() + "' to target '" + correctDatatype.toSingleLineString() + "'");
91                         }
92
93                         if (object.isAsserted(container)) {
94                                 String sclType = needsCustomDatatype ? Layer0Utils.getSCLType(correctDatatype) : null;
95
96                                 Resource type = graph.getPossibleType(objectResource, L0.Literal);
97                                 objectResource = graph.newResource();
98                                 graph.claim(objectResource, L0.InstanceOf, null, type);
99                                 graph.claim(container, property, objectResource);
100                                 if(needsCustomDatatype) {
101                                         graph.addLiteral(objectResource, L0.HasDataType, L0.HasDataType_Inverse, L0.DataType, correctDatatype, datatype_binding);
102                                         graph.addLiteral(objectResource, L0.HasValueType, L0.HasValueType_Inverse, L0.String, sclType, Bindings.STRING);
103                                 }
104                         }
105                         
106                         graph.claimValue(objectResource, value, correctBinding);
107                         return null;
108                         
109                 }
110                 
111         };
112
113     public static String unnamedResourceName(Resource resource) {
114         return "r" + resource.getResourceId();
115     }
116 }