[DMAAP-48] Initial code import
[dmaap/datarouter.git] / datarouter-prov / src / main / java / com / att / research / datarouter / reports / LatencyReport.java
1 /*******************************************************************************\r
2  * ============LICENSE_START==================================================\r
3  * * org.onap.dmaap\r
4  * * ===========================================================================\r
5  * * Copyright © 2017 AT&T Intellectual Property. All rights reserved.\r
6  * * ===========================================================================\r
7  * * Licensed under the Apache License, Version 2.0 (the "License");\r
8  * * you may not use this file except in compliance with the License.\r
9  * * You may obtain a copy of the License at\r
10  * * \r
11  *  *      http://www.apache.org/licenses/LICENSE-2.0\r
12  * * \r
13  *  * Unless required by applicable law or agreed to in writing, software\r
14  * * distributed under the License is distributed on an "AS IS" BASIS,\r
15  * * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
16  * * See the License for the specific language governing permissions and\r
17  * * limitations under the License.\r
18  * * ============LICENSE_END====================================================\r
19  * *\r
20  * * ECOMP is a trademark and service mark of AT&T Intellectual Property.\r
21  * *\r
22  ******************************************************************************/\r
23 \r
24 \r
25 package com.att.research.datarouter.reports;\r
26 \r
27 import java.io.FileNotFoundException;\r
28 import java.io.PrintWriter;\r
29 import java.sql.Connection;\r
30 import java.sql.PreparedStatement;\r
31 import java.sql.ResultSet;\r
32 import java.sql.SQLException;\r
33 import java.util.ArrayList;\r
34 import java.util.List;\r
35 \r
36 import com.att.research.datarouter.provisioning.utils.DB;\r
37 \r
38 /**\r
39  * Generate a per-file latency report.  It reports on the details related to one file published\r
40  * on one feed. This report can be further reduced in order to generate more specific reports\r
41  * based on feed ID or node name. The report is a .csv file containing the following columns:\r
42  * <table>\r
43  * <tr><td>recordid</td><td>the unique record ID assigned to a particular incoming feed</td></tr>\r
44  * <tr><td>feedid</td><td>the Feed ID for this record</td></tr>\r
45  * <tr><td>uri</td><td>the URI of the file delivered</td></tr>\r
46  * <tr><td>size</td><td>the size of the file delivered</td></tr>\r
47  * <tr><td>min</td><td>the minimum latency in delivering this feed to a subscriber (in ms)</td></tr>\r
48  * <tr><td>max</td><td>the maximum latency in delivering this feed to a subscriber (in ms)</td></tr>\r
49  * <tr><td>avg</td><td>the average latency in delivering this feed to all subscribers (in ms)</td></tr>\r
50  * <tr><td>fanout</td><td>the number of subscribers this feed was delivered to</td></tr>\r
51  * </table>\r
52  *\r
53  * @author Robert P. Eby\r
54  * @version $Id: LatencyReport.java,v 1.1 2013/10/28 18:06:53 eby Exp $\r
55  */\r
56 public class LatencyReport extends ReportBase {\r
57         private static final String SELECT_SQL =\r
58                 "select EVENT_TIME, TYPE, PUBLISH_ID, FEED_FILEID, FEEDID, CONTENT_LENGTH from LOG_RECORDS" +\r
59                 " where EVENT_TIME >= ? and EVENT_TIME <= ? order by PUBLISH_ID, EVENT_TIME";\r
60 \r
61         private class Event {\r
62                 public final String type;\r
63                 public final long time;\r
64                 public Event(String t, long tm) {\r
65                         type = t;\r
66                         time = tm;\r
67                 }\r
68         }\r
69         private class Counters {\r
70                 public final String id;\r
71                 public final int feedid;\r
72                 public final long clen;\r
73                 public final String fileid;\r
74                 public final List<Event> events;\r
75                 public Counters(String i, int fid, long c, String s) {\r
76                         id = i;\r
77                         feedid = fid;\r
78                         clen = c;\r
79                         fileid = s;\r
80                         events = new ArrayList<Event>();\r
81                 }\r
82                 private long pubtime;\r
83                 public void addEvent(String t, long tm) {\r
84                         events.add(new Event(t, tm));\r
85                         if (t.equals("pub"))\r
86                                 pubtime = tm;\r
87                 }\r
88                 public long min() {\r
89                         long min = Long.MAX_VALUE;\r
90                         for (Event e : events) {\r
91                                 if (e.type.equals("del")) {\r
92                                         min = Math.min(min, e.time - pubtime);\r
93                                 }\r
94                         }\r
95                         return min;\r
96                 }\r
97                 public long max() {\r
98                         long max = 0;\r
99                         for (Event e : events) {\r
100                                 if (e.type.equals("del")) {\r
101                                         max = Math.max(max, e.time - pubtime);\r
102                                 }\r
103                         }\r
104                         return max;\r
105                 }\r
106                 public long avg() {\r
107                         long total = 0, c = 0;\r
108                         for (Event e : events) {\r
109                                 if (e.type.equals("del")) {\r
110                                         total += e.time - pubtime;\r
111                                         c++;\r
112                                 }\r
113                         }\r
114                         return (c == 0) ? 0 : total/c;\r
115                 }\r
116                 public int fanout() {\r
117                         int n = 0;\r
118                         for (Event e : events) {\r
119                                 if (e.type.equals("del")) {\r
120                                         n++;\r
121                                 }\r
122                         }\r
123                         return n;\r
124                 }\r
125                 @Override\r
126                 public String toString() {\r
127                         return feedid + "," + fileid + "," + clen + "," + min() + "," + max() + "," + avg() + "," + fanout();\r
128                 }\r
129         }\r
130 \r
131         @Override\r
132         public void run() {\r
133                 long start = System.currentTimeMillis();\r
134                 try {\r
135                         DB db = new DB();\r
136                         @SuppressWarnings("resource")\r
137                         Connection conn = db.getConnection();\r
138                         PreparedStatement ps = conn.prepareStatement(SELECT_SQL);\r
139                         ps.setLong(1, from);\r
140                         ps.setLong(2, to);\r
141                         ResultSet rs = ps.executeQuery();\r
142                         PrintWriter os = new PrintWriter(outfile);\r
143                         os.println("recordid,feedid,uri,size,min,max,avg,fanout");\r
144                         Counters c = null;\r
145                         while (rs.next()) {\r
146                                 long etime  = rs.getLong("EVENT_TIME");\r
147                                 String type = rs.getString("TYPE");\r
148                                 String id   = rs.getString("PUBLISH_ID");\r
149                                 String fid  = rs.getString("FEED_FILEID");\r
150                                 int feed    = rs.getInt("FEEDID");\r
151                                 long clen   = rs.getLong("CONTENT_LENGTH");\r
152                                 if (c != null && !id.equals(c.id)) {\r
153                                         String line = id + "," + c.toString();\r
154                                         os.println(line);\r
155                                         c = null;\r
156                                 }\r
157                                 if (c == null) {\r
158                                         c = new Counters(id, feed, clen, fid);\r
159                                 }\r
160                                 if (feed != c.feedid)\r
161                                         System.err.println("Feed ID mismatch, "+feed+" <=> "+c.feedid);\r
162                                 if (clen != c.clen)\r
163                                         System.err.println("Cont Len mismatch, "+clen+" <=> "+c.clen);\r
164 //                              if (fid != c.fileid)\r
165 //                                      System.err.println("File ID mismatch, "+fid+" <=> "+c.fileid);\r
166                                 c.addEvent(type, etime);\r
167                         }\r
168                         rs.close();\r
169                         ps.close();\r
170                         db.release(conn);\r
171                         os.close();\r
172                 } catch (FileNotFoundException e) {\r
173                         System.err.println("File cannot be written: "+outfile);\r
174                 } catch (SQLException e) {\r
175                         e.printStackTrace();\r
176                 }\r
177                 logger.debug("Query time: " + (System.currentTimeMillis()-start) + " ms");\r
178         }\r
179 }\r