001/**
002 * Licensed to the Apache Software Foundation (ASF) under one
003 * or more contributor license agreements.  See the NOTICE file
004 * distributed with this work for additional information
005 * regarding copyright ownership.  The ASF licenses this file
006 * to you under the Apache License, Version 2.0 (the
007 * "License"); you may not use this file except in compliance
008 * with the License.  You may obtain a copy of the License at
009 *
010 *      http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing, software
013 * distributed under the License is distributed on an "AS IS" BASIS,
014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 * See the License for the specific language governing permissions and
016 * limitations under the License.
017 */
018package org.apache.oozie.sla;
019
020import java.sql.Timestamp;
021import java.util.Date;
022import java.util.List;
023
024import javax.persistence.Basic;
025import javax.persistence.Column;
026import javax.persistence.Entity;
027import javax.persistence.Id;
028import javax.persistence.NamedQueries;
029import javax.persistence.NamedQuery;
030import javax.persistence.Table;
031
032import org.apache.oozie.AppType;
033import org.apache.oozie.client.event.SLAEvent;
034import org.apache.oozie.client.rest.JsonBean;
035import org.apache.oozie.client.rest.JsonTags;
036import org.apache.oozie.client.rest.JsonUtils;
037import org.apache.oozie.util.DateUtils;
038import org.apache.openjpa.persistence.jdbc.Index;
039import org.json.simple.JSONArray;
040import org.json.simple.JSONObject;
041
042@Entity
043@Table(name = "SLA_SUMMARY")
044@NamedQueries({
045
046 @NamedQuery(name = "UPDATE_SLA_SUMMARY_FOR_SLA_STATUS", query = "update  SLASummaryBean w set w.slaStatus = :slaStatus, w.eventStatus = :eventStatus, w.eventProcessed = :eventProcessed, w.lastModifiedTS = :lastModifiedTS where w.jobId = :jobId"),
047
048 @NamedQuery(name = "UPDATE_SLA_SUMMARY_FOR_STATUS_ACTUAL_TIMES", query = "update SLASummaryBean w set w.slaStatus = :slaStatus, w.eventStatus = :eventStatus, w.eventProcessed = :eventProcessed, w.jobStatus = :jobStatus, w.lastModifiedTS = :lastModifiedTS, w.actualStartTS = :actualStartTS, w.actualEndTS = :actualEndTS, w.actualDuration = :actualDuration where w.jobId = :jobId"),
049
050 @NamedQuery(name = "UPDATE_SLA_SUMMARY_FOR_ACTUAL_TIMES", query = "update SLASummaryBean w set w.eventProcessed = :eventProcessed, w.actualStartTS = :actualStartTS, w.actualEndTS = :actualEndTS, w.actualEndTS = :actualEndTS, w.actualDuration = :actualDuration, w.lastModifiedTS = :lastModifiedTS where w.jobId = :jobId"),
051
052 @NamedQuery(name = "UPDATE_SLA_SUMMARY_EVENTPROCESSED", query = "update SLASummaryBean w set w.eventProcessed = :eventProcessed where w.jobId = :jobId"),
053
054 @NamedQuery(name = "UPDATE_SLA_SUMMARY_ALL", query = "update SLASummaryBean w set w.jobId = :jobId, w.appName = :appName, w.appType = :appType, w.nominalTimeTS = :nominalTime, w.expectedStartTS = :expectedStartTime, w.expectedEndTS = :expectedEndTime, w.expectedDuration = :expectedDuration, w.jobStatus = :jobStatus, w.slaStatus = :slaStatus, w.eventStatus = :eventStatus, w.lastModifiedTS = :lastModTime, w.user = :user, w.parentId = :parentId, w.eventProcessed = :eventProcessed, w.actualDuration = :actualDuration, w.actualEndTS = :actualEndTS, w.actualStartTS = :actualStartTS where w.jobId = :jobId"),
055
056 @NamedQuery(name = "GET_SLA_SUMMARY", query = "select OBJECT(w) from SLASummaryBean w where w.jobId = :id"),
057
058 @NamedQuery(name = "GET_SLA_SUMMARY_RECORDS_RESTART", query = "select OBJECT(w) from SLASummaryBean w where w.eventProcessed <= 7 AND w.lastModifiedTS >= :lastModifiedTime"),
059
060 @NamedQuery(name = "GET_SLA_SUMMARY_EVENTPROCESSED", query = "select w.eventProcessed from SLASummaryBean w where w.jobId = :id")
061})
062
063/**
064 * Class to store all the SLA related details (summary) per job
065 */
066public class SLASummaryBean implements JsonBean {
067
068    @Id
069    @Basic
070    @Column(name = "job_id")
071    private String jobId;
072
073    @Basic
074    @Index
075    @Column(name = "parent_id")
076    private String parentId;
077
078    @Basic
079    @Index
080    @Column(name = "app_name")
081    private String appName;
082
083    @Basic
084    @Column(name = "app_type")
085    private String appType;
086
087    @Basic
088    @Column(name = "user_name")
089    private String user;
090
091    @Basic
092    @Column(name = "created_time")
093    private Timestamp createdTimeTS = null;
094
095    @Basic
096    @Index
097    @Column(name = "nominal_time")
098    private Timestamp nominalTimeTS = null;
099
100    @Basic
101    @Column(name = "expected_start")
102    private Timestamp expectedStartTS = null;
103
104    @Basic
105    @Column(name = "expected_end")
106    private Timestamp expectedEndTS = null;
107
108    @Basic
109    @Column(name = "expected_duration")
110    private long expectedDuration = -1;
111
112    @Basic
113    @Column(name = "actual_start")
114    private Timestamp actualStartTS = null;
115
116    @Basic
117    @Column(name = "actual_end")
118    private Timestamp actualEndTS = null;
119
120    @Basic
121    @Column(name = "actual_duration")
122    private long actualDuration = -1;
123
124    @Basic
125    @Column(name = "job_status")
126    private String jobStatus;
127
128    @Basic
129    @Column(name = "event_status")
130    private String eventStatus;
131
132    @Basic
133    @Column(name = "sla_status")
134    private String slaStatus;
135
136    @Basic
137    @Index
138    @Column(name = "event_processed")
139    private byte eventProcessed = 0;
140
141    @Basic
142    @Index
143    @Column(name = "last_modified")
144    private Timestamp lastModifiedTS = null;
145
146    public SLASummaryBean() {
147    }
148
149    public SLASummaryBean(SLACalcStatus slaCalc) {
150        SLARegistrationBean reg = slaCalc.getSLARegistrationBean();
151        setId(slaCalc.getId());
152        setAppName(reg.getAppName());
153        setAppType(reg.getAppType());
154        setNominalTime(reg.getNominalTime());
155        setExpectedStart(reg.getExpectedStart());
156        setExpectedEnd(reg.getExpectedEnd());
157        setExpectedDuration(reg.getExpectedDuration());
158        setJobStatus(slaCalc.getJobStatus());
159        setSLAStatus(slaCalc.getSLAStatus());
160        setEventStatus(slaCalc.getEventStatus());
161        setLastModifiedTime(slaCalc.getLastModifiedTime());
162        setUser(reg.getUser());
163        setParentId(reg.getParentId());
164        setEventProcessed(slaCalc.getEventProcessed());
165        setActualDuration(slaCalc.getActualDuration());
166        setActualEnd(slaCalc.getActualEnd());
167        setActualStart(slaCalc.getActualStart());
168    }
169
170    public String getId() {
171        return jobId;
172    }
173
174    public void setId(String jobId) {
175        this.jobId = jobId;
176    }
177
178    public String getParentId() {
179        return parentId;
180    }
181
182    public void setParentId(String parentId) {
183        this.parentId = parentId;
184    }
185
186    public Timestamp getCreatedTimestamp() {
187        return createdTimeTS;
188    }
189
190    public void setCreatedTimestamp(Timestamp createdTime) {
191        this.createdTimeTS = createdTime;
192    }
193
194    public Date getCreatedTime() {
195        return DateUtils.toDate(createdTimeTS);
196    }
197
198    public void setCreatedTime(Date createdTime) {
199        this.createdTimeTS = DateUtils.convertDateToTimestamp(createdTime);
200    }
201
202    public Date getNominalTime() {
203        return DateUtils.toDate(nominalTimeTS);
204    }
205
206    public Timestamp getNominalTimestamp() {
207        return this.nominalTimeTS;
208    }
209
210    public void setNominalTime(Date nominalTime) {
211        this.nominalTimeTS = DateUtils.convertDateToTimestamp(nominalTime);
212    }
213
214
215    public Date getExpectedStart() {
216        return DateUtils.toDate(expectedStartTS);
217    }
218
219    public Timestamp getExpectedStartTimestamp() {
220        return this.expectedStartTS;
221    }
222
223    public void setExpectedStart(Date expectedStart) {
224        this.expectedStartTS = DateUtils.convertDateToTimestamp(expectedStart);
225    }
226
227    public Date getExpectedEnd() {
228        return DateUtils.toDate(expectedEndTS);
229    }
230
231    public Timestamp getExpectedEndTimestamp() {
232        return this.expectedEndTS;
233    }
234    public void setExpectedEnd(Date expectedEnd) {
235        this.expectedEndTS = DateUtils.convertDateToTimestamp(expectedEnd);
236    }
237
238    public long getExpectedDuration() {
239        return expectedDuration;
240    }
241
242    public void setExpectedDuration(long expectedDuration) {
243        this.expectedDuration = expectedDuration;
244    }
245
246    public Date getActualStart() {
247        return DateUtils.toDate(actualStartTS);
248    }
249
250    public Timestamp getActualStartTimestamp() {
251        return this.actualStartTS;
252    }
253
254    public void setActualStart(Date actualStart) {
255        this.actualStartTS = DateUtils.convertDateToTimestamp(actualStart);
256    }
257
258    public Date getActualEnd() {
259        return DateUtils.toDate(actualEndTS);
260    }
261
262    public Timestamp getActualEndTimestamp() {
263        return this.actualEndTS;
264    }
265
266    public void setActualEnd(Date actualEnd) {
267        this.actualEndTS = DateUtils.convertDateToTimestamp(actualEnd);
268    }
269
270    public long getActualDuration() {
271        return actualDuration;
272    }
273
274    public void setActualDuration(long actualDuration) {
275        this.actualDuration = actualDuration;
276    }
277
278    public String getJobStatus() {
279        return jobStatus;
280    }
281
282    public void setJobStatus(String status) {
283        this.jobStatus = status;
284    }
285
286    public SLAEvent.EventStatus getEventStatus() {
287        return (eventStatus != null ? SLAEvent.EventStatus.valueOf(eventStatus) : null);
288    }
289
290    public void setEventStatus(SLAEvent.EventStatus eventStatus) {
291        this.eventStatus = (eventStatus != null ? eventStatus.name() : null);
292    }
293
294    public SLAEvent.SLAStatus getSLAStatus() {
295        return (slaStatus != null ? SLAEvent.SLAStatus.valueOf(slaStatus) : null);
296    }
297
298    public String getSLAStatusString() {
299        return slaStatus;
300    }
301
302    public String getEventStatusString() {
303        return eventStatus;
304    }
305
306    public void setSLAStatus(SLAEvent.SLAStatus stage) {
307        this.slaStatus = (stage != null ? stage.name() : null);
308    }
309
310    public String getUser() {
311        return user;
312    }
313
314    public void setUser(String user) {
315        this.user = user;
316    }
317
318    public String getAppName() {
319        return appName;
320    }
321
322    public void setAppName(String appName) {
323        this.appName = appName;
324    }
325
326    public AppType getAppType() {
327        return AppType.valueOf(appType);
328    }
329
330    public void setAppType(AppType appType) {
331        this.appType = appType.toString();
332    }
333
334    public byte getEventProcessed() {
335        return eventProcessed;
336    }
337
338    public void setEventProcessed(int eventProcessed) {
339        this.eventProcessed = (byte)eventProcessed;
340    }
341
342    public Date getLastModifiedTime() {
343        return DateUtils.toDate(lastModifiedTS);
344    }
345
346    public Timestamp getLastModifiedTimestamp() {
347        return this.lastModifiedTS;
348    }
349
350    public void setLastModifiedTime(Date lastModified) {
351        this.lastModifiedTS = DateUtils.convertDateToTimestamp(lastModified);
352    }
353
354    @SuppressWarnings("unchecked")
355    @Override
356    public JSONObject toJSONObject() {
357        JSONObject json = new JSONObject();
358        json.put(JsonTags.SLA_SUMMARY_ID, jobId);
359        if (parentId != null) {
360            json.put(JsonTags.SLA_SUMMARY_PARENT_ID, parentId);
361        }
362        json.put(JsonTags.SLA_SUMMARY_APP_NAME, appName);
363        json.put(JsonTags.SLA_SUMMARY_APP_TYPE, appType);
364        json.put(JsonTags.SLA_SUMMARY_USER, user);
365        json.put(JsonTags.SLA_SUMMARY_NOMINAL_TIME, nominalTimeTS.getTime());
366        if (expectedStartTS != null) {
367            json.put(JsonTags.SLA_SUMMARY_EXPECTED_START, expectedStartTS.getTime());
368        }
369        else {
370            json.put(JsonTags.SLA_SUMMARY_EXPECTED_START, null);
371        }
372        if (actualStartTS != null) {
373            json.put(JsonTags.SLA_SUMMARY_ACTUAL_START, actualStartTS.getTime());
374        }
375        else {
376            json.put(JsonTags.SLA_SUMMARY_ACTUAL_START, null);
377        }
378        json.put(JsonTags.SLA_SUMMARY_EXPECTED_END, expectedEndTS.getTime());
379        if (actualEndTS != null) {
380            json.put(JsonTags.SLA_SUMMARY_ACTUAL_END, actualEndTS.getTime());
381        }
382        else {
383            json.put(JsonTags.SLA_SUMMARY_ACTUAL_END, null);
384        }
385        json.put(JsonTags.SLA_SUMMARY_EXPECTED_DURATION, expectedDuration);
386        json.put(JsonTags.SLA_SUMMARY_ACTUAL_DURATION, actualDuration);
387        json.put(JsonTags.SLA_SUMMARY_JOB_STATUS, jobStatus);
388        json.put(JsonTags.SLA_SUMMARY_SLA_STATUS, slaStatus);
389        json.put(JsonTags.SLA_SUMMARY_LAST_MODIFIED, lastModifiedTS.getTime());
390        return json;
391    }
392
393    @SuppressWarnings("unchecked")
394    @Override
395    public JSONObject toJSONObject(String timeZoneId) {
396        if (timeZoneId == null) {
397            return toJSONObject();
398        }
399        else {
400            JSONObject json = new JSONObject();
401            json.put(JsonTags.SLA_SUMMARY_ID, jobId);
402            if (parentId != null) {
403                json.put(JsonTags.SLA_SUMMARY_PARENT_ID, parentId);
404            }
405            json.put(JsonTags.SLA_SUMMARY_APP_NAME, appName);
406            json.put(JsonTags.SLA_SUMMARY_APP_TYPE, appType);
407            json.put(JsonTags.SLA_SUMMARY_USER, user);
408            json.put(JsonTags.SLA_SUMMARY_NOMINAL_TIME, JsonUtils.formatDateRfc822(nominalTimeTS, timeZoneId));
409            if (expectedStartTS != null) {
410                json.put(JsonTags.SLA_SUMMARY_EXPECTED_START, JsonUtils.formatDateRfc822(expectedStartTS, timeZoneId));
411            }
412            else {
413                json.put(JsonTags.SLA_SUMMARY_EXPECTED_START, null);
414            }
415            if (actualStartTS != null) {
416                json.put(JsonTags.SLA_SUMMARY_ACTUAL_START, JsonUtils.formatDateRfc822(actualStartTS, timeZoneId));
417            }
418            else {
419                json.put(JsonTags.SLA_SUMMARY_ACTUAL_START, null);
420            }
421            json.put(JsonTags.SLA_SUMMARY_EXPECTED_END, JsonUtils.formatDateRfc822(expectedEndTS, timeZoneId));
422            if (actualEndTS != null) {
423                json.put(JsonTags.SLA_SUMMARY_ACTUAL_END, JsonUtils.formatDateRfc822(actualEndTS, timeZoneId));
424            }
425            else {
426                json.put(JsonTags.SLA_SUMMARY_ACTUAL_END, null);
427            }
428            json.put(JsonTags.SLA_SUMMARY_EXPECTED_DURATION, expectedDuration);
429            json.put(JsonTags.SLA_SUMMARY_ACTUAL_DURATION, actualDuration);
430            json.put(JsonTags.SLA_SUMMARY_JOB_STATUS, jobStatus);
431            json.put(JsonTags.SLA_SUMMARY_SLA_STATUS, slaStatus);
432            json.put(JsonTags.SLA_SUMMARY_LAST_MODIFIED, JsonUtils.formatDateRfc822(lastModifiedTS, timeZoneId));
433            return json;
434        }
435    }
436
437    /**
438     * Convert a sla summary list into a json object.
439     *
440     * @param slaSummaryList sla summary list.
441     * @param timeZoneId time zone to use for dates in the JSON array.
442     * @return the corresponding JSON object.
443     */
444    @SuppressWarnings("unchecked")
445    public static JSONObject toJSONObject(List<? extends SLASummaryBean> slaSummaryList, String timeZoneId) {
446        JSONObject json = new JSONObject();
447        JSONArray array = new JSONArray();
448        if (slaSummaryList != null) {
449            for (SLASummaryBean summary : slaSummaryList) {
450                array.add(summary.toJSONObject(timeZoneId));
451            }
452        }
453        json.put(JsonTags.SLA_SUMMARY_LIST, array);
454        return json;
455    }
456
457}