bb4023abc43f2c76e458f0866bc24677e06a4f01
[ccsdk/features.git] /
1 /*
2  * ============LICENSE_START=======================================================
3  * ONAP : ccsdk features
4  * ================================================================================
5  * Copyright (C) 2020 highstreet technologies GmbH Intellectual Property.
6  * All rights reserved.
7  * ================================================================================
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *     http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  * ============LICENSE_END=========================================================
20  *
21  */
22 package org.onap.ccsdk.features.sdnr.wt.dataprovider.http;
23
24 import java.io.BufferedReader;
25 import java.io.IOException;
26 import java.io.InputStream;
27 import java.io.InputStreamReader;
28 import java.io.UnsupportedEncodingException;
29 import java.net.URLDecoder;
30 import java.util.ArrayList;
31 import java.util.List;
32 import java.util.regex.Matcher;
33 import java.util.regex.Pattern;
34 import javax.servlet.ServletException;
35 import javax.servlet.http.HttpServlet;
36 import javax.servlet.http.HttpServletRequest;
37 import javax.servlet.http.HttpServletResponse;
38 import org.json.JSONObject;
39 import org.onap.ccsdk.features.sdnr.wt.common.database.HtDatabaseClient;
40 import org.onap.ccsdk.features.sdnr.wt.dataprovider.impl.DataTreeProviderImpl;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.data.provider.rev201110.Entity;
42 import org.slf4j.Logger;
43 import org.slf4j.LoggerFactory;
44
45 /**
46  * @author Michael Dürre
47  *
48  */
49 public class DataTreeHttpServlet extends HttpServlet {
50
51     public enum FilterMode {
52         Strict, //show only filtered items and their parents
53         Lazy //show root items (and all their children) which have matches inside
54     }
55
56     /**
57      *
58      */
59     private static final long serialVersionUID = 1L;
60     private final DataTreeProviderImpl dataTreeProvider;
61     private static final Logger LOG = LoggerFactory.getLogger(DataTreeHttpServlet.class);
62
63     public DataTreeHttpServlet() {
64         super();
65         this.dataTreeProvider = new DataTreeProviderImpl();
66     }
67
68     /**
69      * @param client
70      */
71     public void setDatabaseClient(HtDatabaseClient client) {
72         this.dataTreeProvider.setDatabaseClient(client);
73
74     }
75
76     public static String readPayload(HttpServletRequest request) throws IOException {
77
78         String body = null;
79         StringBuilder stringBuilder = new StringBuilder();
80         BufferedReader bufferedReader = null;
81
82         try {
83             InputStream inputStream = request.getInputStream();
84             if (inputStream != null) {
85                 bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
86                 char[] charBuffer = new char[128];
87                 int bytesRead = -1;
88                 while ((bytesRead = bufferedReader.read(charBuffer)) > 0) {
89                     stringBuilder.append(charBuffer, 0, bytesRead);
90                 }
91             } else {
92                 stringBuilder.append("");
93             }
94         } catch (IOException ex) {
95             throw ex;
96         } finally {
97             if (bufferedReader != null) {
98                 try {
99                     bufferedReader.close();
100                 } catch (IOException ex) {
101                     throw ex;
102                 }
103             }
104         }
105
106         body = stringBuilder.toString();
107         return body;
108     }
109
110     @Override
111     protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
112         final String uri = req.getRequestURI();
113         LOG.debug("GET request for {}", uri);
114         final EntityWithTree e = getEntity(uri);
115         if (e != null) {
116             LOG.info("GET request for {} to e={} with tree={}", uri, e.entity, e.tree);
117             switch (e.entity) {
118                 case Inventoryequipment:
119                     DataTreeObject o = this.dataTreeProvider.readInventoryTree(e.tree, null, FilterMode.Lazy);
120                     this.doJsonResponse(resp, o);
121                     break;
122                 default:
123                     this.notAvailble(resp);
124                     break;
125             }
126         } else {
127             LOG.debug("unable to find entity for uri {}", uri);
128         }
129     }
130
131     @Override
132     protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
133         final String uri = req.getRequestURI();
134         String filter = null;
135         FilterMode mode = FilterMode.Lazy;
136         try {
137             final String body = readPayload(req);
138             JSONObject data = new JSONObject(body);
139             if (data.has("query")) {
140                 filter = data.getString("query");
141             }
142             if (data.has("mode")) {
143                 mode = data.getString("mode").equals("lazy") ? FilterMode.Lazy : FilterMode.Strict;
144             }
145
146
147         } catch (Exception e) {
148             LOG.warn("problem reading payload: {}", e);
149         }
150         LOG.debug("POST request for {}", uri);
151         final EntityWithTree e = getEntity(uri);
152         if (e != null) {
153             switch (e.entity) {
154                 case Inventoryequipment:
155                     DataTreeObject o = this.dataTreeProvider.readInventoryTree(e.tree, filter, mode);
156                     this.doJsonResponse(resp, o);
157                     break;
158                 default:
159                     this.notAvailble(resp);
160                     break;
161             }
162         }
163     }
164
165     /**
166      * @param resp
167      */
168     private void notAvailble(HttpServletResponse resp) {
169         try {
170             resp.sendError(HttpServletResponse.SC_NOT_FOUND);
171         } catch (IOException e) {
172
173         }
174     }
175
176     public static EntityWithTree getEntity(String uri) {
177         final String regex = "^\\/tree\\/read-(.*)-tree\\/?(.*)$";
178         final Pattern pattern = Pattern.compile(regex);
179         final Matcher matcher = pattern.matcher(uri);
180         Entity e = null;
181         if (matcher.find() && matcher.groupCount() > 0) {
182             try {
183                 e = Entity.forName(matcher.group(1)).get();
184                 return new EntityWithTree(e, matcher.groupCount() > 1 ? matcher.group(2) : null);
185             } catch (Exception e2) {
186                 LOG.warn("unable to parse {} into entity: {}", matcher.group(2), e2);
187             }
188         }
189         return null;
190
191     }
192
193     private void doJsonResponse(HttpServletResponse resp, DataTreeObject data) {
194         resp.setHeader("Content-Type", "application/json");
195         try {
196             resp.getWriter().write(data.toJSON());
197         } catch (IOException e) {
198             LOG.warn("problem sending response: {}", e);
199         }
200     }
201
202     public static class EntityWithTree {
203         public final Entity entity;
204         public final List<String> tree;
205
206         @Override
207         public String toString() {
208             return "EntityWithTree [entity=" + entity + ", tree=" + tree + "]";
209         }
210
211         public EntityWithTree(Entity e, String tree) {
212             this.entity = e;
213             if (tree != null) {
214                 if (tree.startsWith("/")) {
215                     tree = tree.substring(1);
216                 }
217                 if (tree.endsWith("/")) {
218                     tree = tree.substring(0, tree.length() - 1);
219                 }
220                 String[] tmp = tree.split("\\/");
221                 this.tree = new ArrayList<>();
222                 for (int i = 0; i < tmp.length; i++) {
223                     try {
224                         String s = URLDecoder.decode(tmp[i], "utf-8");
225                         if (s != null && s.length() > 0) {
226                             this.tree.add(s);
227                         }
228                     } catch (UnsupportedEncodingException e1) {
229                         LOG.warn("problem urldecode {}: {}", tmp[i], e);
230                     }
231                 }
232             } else {
233                 this.tree = null;
234             }
235         }
236     }
237 }