[AAI-2175] Change aai champ container processes to run as non-root on the host
[aai/champ.git] / champ-lib / champ-core / src / main / java / org / onap / aai / champcore / graph / impl / InMemoryChampGraphImpl.java
1 /**
2  * ============LICENSE_START==========================================
3  * org.onap.aai
4  * ===================================================================
5  * Copyright Â© 2017-2018 AT&T Intellectual Property. All rights reserved.
6  * Copyright Â© 2017-2018 Amdocs
7  * Modifications Copyright (C) 2019 IBM
8  * ===================================================================
9  * Licensed under the Apache License, Version 2.0 (the "License");
10  * you may not use this file except in compliance with the License.
11  * You may obtain a copy of the License at
12  *
13  *        http://www.apache.org/licenses/LICENSE-2.0
14  *
15  * Unless required by applicable law or agreed to in writing, software
16  * distributed under the License is distributed on an "AS IS" BASIS,
17  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18  * See the License for the specific language governing permissions and
19  * limitations under the License.
20  * ============LICENSE_END============================================
21  */
22 package org.onap.aai.champcore.graph.impl;
23
24 import java.util.HashMap;
25 import java.util.Map;
26 import java.util.Optional;
27 import java.util.concurrent.ConcurrentHashMap;
28 import java.util.stream.Stream;
29
30 import org.apache.tinkerpop.gremlin.process.traversal.dsl.graph.GraphTraversal;
31 import org.apache.tinkerpop.gremlin.structure.Edge;
32 import org.apache.tinkerpop.gremlin.structure.Vertex;
33 import org.apache.tinkerpop.gremlin.tinkergraph.structure.TinkerGraph;
34 import org.onap.aai.champcore.ChampCapabilities;
35 import org.onap.aai.champcore.ChampTransaction;
36 import org.onap.aai.champcore.NoOpTinkerPopTransaction;
37 import org.onap.aai.champcore.exceptions.ChampIndexNotExistsException;
38 import org.onap.aai.champcore.model.ChampObjectIndex;
39 import org.onap.aai.champcore.model.ChampRelationshipIndex;
40 import org.onap.aai.champcore.schema.ChampSchemaEnforcer;
41 import org.onap.aai.champcore.schema.DefaultChampSchemaEnforcer;
42
43 public final class InMemoryChampGraphImpl extends AbstractTinkerpopChampGraph {
44
45         private static final ChampCapabilities CAPABILITIES = new ChampCapabilities() {
46
47                 @Override
48                 public boolean canDeleteObjectIndices() {
49                         return true;
50                 }
51
52                 @Override
53                 public boolean canDeleteRelationshipIndices() {
54                         return true;
55                 }
56         };
57
58         private final ConcurrentHashMap<String, ChampObjectIndex> objectIndices;
59         private final ConcurrentHashMap<String, ChampRelationshipIndex> relationshipIndices;
60
61         private final ChampSchemaEnforcer schemaEnforcer;
62         private final TinkerGraph graph;
63
64         private InMemoryChampGraphImpl(Builder builder) {
65             super(builder.graphConfiguration);
66                 this.graph = TinkerGraph.open();
67         
68                 this.objectIndices = new ConcurrentHashMap<>();
69                 this.relationshipIndices = new ConcurrentHashMap<>();
70
71                 this.schemaEnforcer = builder.schemaEnforcer;
72         }
73
74         @Override
75     public ChampTransaction getOrCreateTransactionInstance(Optional<ChampTransaction> transaction) {
76
77           return new NoOpTinkerPopTransaction(getGraph());
78
79         }
80            
81         public static class Builder {
82             private final Map<String, Object> graphConfiguration = new HashMap<String, Object> ();
83                 private ChampSchemaEnforcer schemaEnforcer = new DefaultChampSchemaEnforcer();
84
85                 public Builder() {}
86
87                 public Builder schemaEnforcer(ChampSchemaEnforcer schemaEnforcer) {
88                         this.schemaEnforcer = schemaEnforcer;
89                         return this;
90                 }
91
92               public Builder properties(Map<String, Object> properties) {
93             
94             this.graphConfiguration.putAll(properties);
95             return this;
96         }
97
98         public Builder property(String path, Object value) {
99            
100             graphConfiguration.put(path, value);
101             return this;
102         }
103         
104                 public InMemoryChampGraphImpl build() {
105                         return new InMemoryChampGraphImpl(this);
106                 }
107         }
108
109         protected ChampSchemaEnforcer getSchemaEnforcer() {
110                 return schemaEnforcer;
111         }
112
113         @Override
114         protected TinkerGraph getGraph() {
115                 return graph;
116         }
117
118         
119         private ConcurrentHashMap<String, ChampObjectIndex> getObjectIndices() {
120                 return objectIndices;
121         }
122
123         private ConcurrentHashMap<String, ChampRelationshipIndex> getRelationshipIndices() {
124                 return relationshipIndices;
125         }
126
127         @Override
128         public void executeStoreObjectIndex(ChampObjectIndex index) {
129           
130                 if (isShutdown()) throw new IllegalStateException("Cannot call storeObjectIndex() after shutdown has been initiated");
131
132                 getGraph().createIndex(index.getFields().get(0).getName(), Vertex.class);
133                 getObjectIndices().put(index.getName(), index);
134         }
135
136         @Override
137         public Optional<ChampObjectIndex> retrieveObjectIndex(String indexName) {
138                 if (isShutdown()) throw new IllegalStateException("Cannot call retrieveObjectIndex() after shutdown has been initiated");
139
140                 if (getObjectIndices().containsKey(indexName))
141                         return Optional.of(getObjectIndices().get(indexName));
142                         
143                 return Optional.empty();
144         }
145
146         @Override
147         public Stream<ChampObjectIndex> retrieveObjectIndices() {
148                 if (isShutdown()) throw new IllegalStateException("Cannot call retrieveObjectIndices() after shutdown has been initiated");
149
150                 return getObjectIndices().values().stream();
151         }
152
153         public void executeDeleteObjectIndex(String indexName) throws ChampIndexNotExistsException {
154                 if (isShutdown()) throw new IllegalStateException("Cannot call deleteObjectIndex() after shutdown has been initiated");
155
156                 final ChampObjectIndex objectIndex = getObjectIndices().remove(indexName);
157
158                 if (objectIndex == null) throw new ChampIndexNotExistsException();
159
160                 getGraph().dropIndex(objectIndex.getFields().get(0).getName(), Vertex.class);
161         }
162
163         public void executeStoreRelationshipIndex(ChampRelationshipIndex index) {
164                 if (isShutdown()) throw new IllegalStateException("Cannot call storeRelationshipIndex() after shutdown has been initiated");
165
166                 getGraph().createIndex(index.getField().getName(), Edge.class);
167                 getRelationshipIndices().put(index.getName(), index);
168         }
169
170         @Override
171         public Optional<ChampRelationshipIndex> retrieveRelationshipIndex(String indexName) {
172                 if (isShutdown()) throw new IllegalStateException("Cannot call retrieveRelationshipIndex() after shutdown has been initiated");
173
174                 if (getRelationshipIndices().containsKey(indexName)) {
175                         return Optional.of(getRelationshipIndices().get(indexName));
176                 }
177                 
178                 return Optional.empty();
179         }
180
181         @Override
182         public Stream<ChampRelationshipIndex> retrieveRelationshipIndices() {
183                 if (isShutdown()) throw new IllegalStateException("Cannot call retrieveRelationshipIndices() after shutdown has been initiated");
184
185                 return getRelationshipIndices().values().stream();
186         }
187
188         public void executeDeleteRelationshipIndex(String indexName) throws ChampIndexNotExistsException {
189                 if (isShutdown()) throw new IllegalStateException("Cannot call deleteRelationshipIndex() after shutdown has been initiated");
190
191                 final ChampRelationshipIndex relationshipIndex = getRelationshipIndices().remove(indexName);
192
193                 if (relationshipIndex == null) throw new ChampIndexNotExistsException();
194                 
195                 getGraph().dropIndex(relationshipIndex.getField().getName(), Edge.class);
196         }
197
198         @Override
199         public ChampCapabilities capabilities() {
200                 return CAPABILITIES;
201         }
202
203         @Override
204         public GraphTraversal<?, ?> hasLabel(GraphTraversal<?, ?> query, Object type) {
205                 return query.hasLabel((String)type, (String)type);
206         }
207
208   @Override
209   public void createDefaultIndexes() {
210     
211   }
212 }