re base code
[sdc.git] / catalog-dao / src / main / java / org / openecomp / sdc / be / dao / neo4j / CypherTranslator.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * 
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  * 
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20
21 package org.openecomp.sdc.be.dao.neo4j;
22
23 import org.apache.commons.lang3.tuple.ImmutablePair;
24 import org.openecomp.sdc.be.dao.graph.datatype.GraphElement;
25 import org.openecomp.sdc.be.dao.graph.datatype.GraphNode;
26 import org.openecomp.sdc.be.dao.graph.datatype.GraphRelation;
27 import org.openecomp.sdc.be.dao.graph.datatype.RelationEndPoint;
28 import org.openecomp.sdc.be.dao.neo4j.filters.MatchFilter;
29 import org.openecomp.sdc.be.dao.neo4j.filters.RecursiveByRelationFilter;
30 import org.openecomp.sdc.be.dao.neo4j.filters.RecursiveFilter;
31 import org.openecomp.sdc.be.dao.utils.DaoUtils;
32
33 import java.util.List;
34 import java.util.Map;
35
36 public class CypherTranslator {
37
38         public String translate(BatchBuilder builder) {
39                 String json = null;
40                 StringBuilder statementList = new StringBuilder();
41
42                 List<GraphElement> elements = builder.getElements();
43                 int statementCounter = 0;
44                 for (GraphElement element : elements) {
45                         String singleStatementBody = null;
46                         switch (element.getElementType()) {
47                         case Node:
48                                 singleStatementBody = prepareNodeStatement(element);
49                                 break;
50                         case Relationship:
51                                 singleStatementBody = prepareRelationStatement(element);
52                                 break;
53                         }
54                         if (singleStatementBody != null && !singleStatementBody.isEmpty()) {
55
56                                 String singleStatement = CypherTemplates.RegularStatementTemplate.replace("$statement$",
57                                                 singleStatementBody);
58
59                                 statementList.append(singleStatement);
60                         }
61                         ++statementCounter;
62                         if (statementCounter < elements.size() && singleStatementBody != null) {
63                                 statementList.append(",");
64                         }
65
66                 }
67                 json = CypherTemplates.BatchTemplate.replace("$statementList$", statementList.toString());
68                 return json;
69         }
70
71         private String prepareNodeStatement(GraphElement element) {
72                 if (element instanceof GraphNode) {
73                         GraphNode node = (GraphNode) element;
74
75                         switch (node.getAction()) {
76                         case Create:
77                                 return createNodeStatement(node);
78                         case Update:
79                                 return updateNodeStatement(node);
80                         case Delete:
81                                 // TODO
82                                 break;
83                         default:
84                                 break;
85                         }
86                 }
87                 return null;
88         }
89
90         private String updateNodeStatement(GraphNode node) {
91                 String singleStatement = CypherTemplates.UpdateNodeStatementTemplate.replace("$label$", node.getLabel());
92                 String filter = prepareKeyValueFilter(node);
93
94                 singleStatement = singleStatement.replace("$filter$", filter);
95
96                 singleStatement = singleStatement.replace("$props$", DaoUtils.convertToJson(node.toGraphMap()));
97
98                 return singleStatement;
99         }
100
101         private String createNodeStatement(GraphNode node) {
102                 String singleStatement = CypherTemplates.CreateSingleNodeTemplate.replace("$label$", node.getLabel());
103
104                 singleStatement = singleStatement.replace("$props$", DaoUtils.convertToJson(node.toGraphMap()));
105                 return singleStatement;
106         }
107
108         private String prepareRelationStatement(GraphElement element) {
109                 if (element instanceof GraphRelation) {
110
111                         GraphRelation relation = (GraphRelation) element;
112
113                         switch (relation.getAction()) {
114                         case Create:
115                                 return createRelationStatement(relation);
116                         case Update:
117                                 return updateRelationStatement(relation);
118                         case Delete:
119                                 // TODO
120                                 break;
121                         default:
122                                 break;
123                         }
124                 }
125                 return null;
126         }
127
128         private String createRelationStatement(GraphRelation relation) {
129                 RelationEndPoint from = relation.getFrom();
130                 String singleStatement;
131
132                 Map<String, Object> props = relation.toGraphMap();
133                 if (props == null || props.isEmpty()) {
134                         singleStatement = CypherTemplates.CreateRelationTemplateNoProps.replace("$labelFrom$",
135                                         from.getLabel().getName());
136                 } else {
137                         singleStatement = CypherTemplates.CreateRelationTemplate.replace("$labelFrom$", from.getLabel().getName());
138                         singleStatement = singleStatement.replace("$props$", DaoUtils.convertToJson(props));
139                 }
140
141                 singleStatement = singleStatement.replace("$idNameFrom$", from.getIdName());
142                 singleStatement = singleStatement.replace("$idValueFrom$", from.getIdValue().toString());
143
144                 RelationEndPoint to = relation.getTo();
145                 singleStatement = singleStatement.replace("$labelTo$", to.getLabel().getName());
146                 singleStatement = singleStatement.replace("$idNameTo$", to.getIdName());
147                 singleStatement = singleStatement.replace("$idvalueTo$", to.getIdValue().toString());
148
149                 singleStatement = singleStatement.replace("$type$", relation.getType());
150                 return singleStatement;
151         }
152
153         private String updateRelationStatement(GraphRelation relation) {
154                 // TODO
155                 return null;
156         }
157
158         private String prepareKeyValueFilter(GraphNode node) {
159                 StringBuilder sb = new StringBuilder();
160
161                 ImmutablePair<String, Object> keyValueId = node.getKeyValueId();
162
163                 sb.append(keyValueId.getKey()).append(":");
164                 if (keyValueId.getValue() instanceof String) {
165                         sb.append("'");
166                 }
167                 sb.append(keyValueId.getValue());
168
169                 if (keyValueId.getValue() instanceof String) {
170                         sb.append("'");
171                 }
172
173                 return sb.toString();
174         }
175
176         public String translateGet(RecursiveFilter filter) {
177                 String requestJson = null;
178                 String statement;
179
180                 if (filter instanceof RecursiveByRelationFilter) {
181                         RecursiveByRelationFilter byRelationFilter = (RecursiveByRelationFilter) filter;
182
183                         statement = CypherTemplates.GetByRelationNodeRecursiveTemplate.replace("$labelNode$",
184                                         byRelationFilter.getNode().getLabel());
185                         String keyValueId = prepareKeyValueFilter(byRelationFilter.getNode());
186
187                         statement = statement.replace("$propsNode$", keyValueId);
188
189                         statement = statement.replace("$type$", byRelationFilter.getRelationType());
190
191                         String relationProps = prepareFilterBody(filter);
192                         statement = statement.replace("$propsRel$", relationProps);
193                         statement = statement.replace("$labelSrc$", filter.getNodeType().getName());
194
195                 } else {
196
197                         statement = CypherTemplates.GetNodeRecursiveTemplate.replace("$label$", filter.getNodeType().getName());
198
199                         // replace filter
200                         if (filter.getProperties().isEmpty()) {
201                                 // get all records by label
202                                 statement = statement.replace("{$filter$}", "");
203                         } else {
204                                 String filterStr = prepareFilterBody(filter);
205                                 statement = statement.replace("$filter$", filterStr);
206                         }
207                 }
208
209                 if (filter.getChildRelationTypes() == null || filter.getChildRelationTypes().isEmpty()) {
210                         statement = statement.replace("$typesList$", "");
211
212                 } else {
213                         StringBuilder typesList = new StringBuilder();
214                         int count = 0;
215                         for (String type : filter.getChildRelationTypes()) {
216                                 typesList.append(":").append(type);
217                                 ++count;
218                                 if (count < filter.getChildRelationTypes().size()) {
219                                         typesList.append("|");
220                                 }
221                         }
222                         statement = statement.replace("$typesList$", typesList.toString());
223                 }
224                 String singleStatement = CypherTemplates.RegularStatementTemplate.replace("$statement$", statement);
225                 requestJson = CypherTemplates.BatchTemplate.replace("$statementList$", singleStatement);
226
227                 return requestJson;
228         }
229
230         public static String prepareFilterBody(MatchFilter filter) {
231                 StringBuilder sb = new StringBuilder();
232                 int count = 0;
233                 int size = filter.getProperties().entrySet().size();
234                 for (Map.Entry<String, Object> entry : filter.getProperties().entrySet()) {
235                         sb.append(entry.getKey()).append(":");
236                         if (entry.getValue() instanceof String) {
237                                 sb.append("'");
238                         }
239                         sb.append(entry.getValue());
240                         if (entry.getValue() instanceof String) {
241                                 sb.append("'");
242                         }
243                         ++count;
244                         if (count < size) {
245                                 sb.append(",");
246                         }
247                 }
248                 return sb.toString();
249         }
250
251 }