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 */
018
019package org.apache.oozie;
020
021import org.apache.hadoop.io.Writable;
022import org.apache.oozie.client.WorkflowAction;
023import org.apache.oozie.client.WorkflowJob;
024import org.apache.oozie.client.rest.JsonBean;
025import org.apache.oozie.client.rest.JsonTags;
026import org.apache.oozie.client.rest.JsonUtils;
027import org.apache.oozie.util.DateUtils;
028import org.apache.oozie.util.WritableUtils;
029import org.apache.oozie.workflow.WorkflowInstance;
030import org.apache.oozie.workflow.lite.LiteWorkflowInstance;
031import org.apache.openjpa.persistence.jdbc.Index;
032import org.apache.openjpa.persistence.jdbc.Strategy;
033import org.json.simple.JSONArray;
034import org.json.simple.JSONObject;
035
036import javax.persistence.Basic;
037import javax.persistence.Column;
038import javax.persistence.Entity;
039import javax.persistence.Id;
040import javax.persistence.Lob;
041import javax.persistence.NamedQueries;
042import javax.persistence.NamedQuery;
043import javax.persistence.Table;
044import javax.persistence.Transient;
045import java.io.DataInput;
046import java.io.DataOutput;
047import java.io.IOException;
048import java.sql.Timestamp;
049import java.text.MessageFormat;
050import java.util.ArrayList;
051import java.util.Date;
052import java.util.List;
053
054@Entity
055
056@NamedQueries({
057
058    @NamedQuery(name = "UPDATE_WORKFLOW", query = "update WorkflowJobBean w set w.appName = :appName, w.appPath = :appPath,"
059            + " w.conf = :conf, w.group = :groupName, w.run = :run, w.user = :user, w.createdTimestamp = :createdTime,"
060            + " w.endTimestamp = :endTime, w.externalId = :externalId, w.lastModifiedTimestamp = :lastModTime,w.logToken "
061            + "= :logToken, w.protoActionConf = :protoActionConf, w.slaXml =:slaXml, w.startTimestamp = :startTime, w.statusStr "
062            + "= :status, w.wfInstance = :wfInstance where w.id = :id"),
063
064    @NamedQuery(name = "UPDATE_WORKFLOW_MODTIME", query = "update WorkflowJobBean w set w.lastModifiedTimestamp = :lastModTime"
065            + " where w.id = :id"),
066
067    @NamedQuery(name = "UPDATE_WORKFLOW_STATUS_MODTIME", query = "update WorkflowJobBean w set w.statusStr = :status,"
068            + " w.lastModifiedTimestamp = :lastModTime where w.id = :id"),
069
070    @NamedQuery(name = "UPDATE_WORKFLOW_PARENT_MODIFIED", query = "update WorkflowJobBean w set w.parentId = :parentId,"
071            + " w.lastModifiedTimestamp = :lastModTime where w.id = :id"),
072
073    @NamedQuery(name = "UPDATE_WORKFLOW_STATUS_INSTANCE_MODIFIED", query = "update WorkflowJobBean w set w.statusStr = :status,"
074            + " w.wfInstance = :wfInstance, w.lastModifiedTimestamp = :lastModTime where w.id = :id"),
075
076    @NamedQuery(name = "UPDATE_WORKFLOW_STATUS_INSTANCE_MOD_END", query = "update WorkflowJobBean w set w.statusStr = :status,"
077            + " w.wfInstance = :wfInstance, w.lastModifiedTimestamp = :lastModTime, w.endTimestamp = :endTime where w.id = :id"),
078
079    @NamedQuery(name = "UPDATE_WORKFLOW_STATUS_INSTANCE_MOD_START_END", query = "update WorkflowJobBean w set w.statusStr "
080            + "= :status, w.wfInstance = :wfInstance, w.lastModifiedTimestamp = :lastModTime, w.startTimestamp = :startTime,"
081            + " w.endTimestamp = :endTime where w.id = :id"),
082
083    @NamedQuery(name = "UPDATE_WORKFLOW_RERUN", query = "update WorkflowJobBean w set w.appName = :appName, w.protoActionConf "
084            + "= :protoActionConf, w.appPath = :appPath, w.conf = :conf, w.logToken = :logToken, w.user = :user, w.group "
085            + "= :group, w.externalId = :externalId, w.endTimestamp = :endTime, w.run = :run, w.statusStr = :status,"
086            + " w.wfInstance = :wfInstance, w.lastModifiedTimestamp = :lastModTime where w.id = :id"),
087
088    @NamedQuery(name = "DELETE_WORKFLOW", query = "delete from WorkflowJobBean w where w.id IN (:id)"),
089
090    @NamedQuery(name = "GET_WORKFLOWS", query = "select OBJECT(w) from WorkflowJobBean w order by w.startTimestamp desc"),
091
092    @NamedQuery(name = "GET_WORKFLOWS_COLUMNS", query = "select w.id, w.appName, w.statusStr, w.run, w.user, w.group,"
093            + " w.createdTimestamp, w.startTimestamp, w.lastModifiedTimestamp, w.endTimestamp, w.externalId, w.parentId "
094            + "from WorkflowJobBean w order by w.createdTimestamp desc"),
095
096    @NamedQuery(name = "GET_WORKFLOWS_COUNT", query = "select count(w) from WorkflowJobBean w"),
097
098    @NamedQuery(name = "GET_COMPLETED_WORKFLOWS_OLDER_THAN", query = "select w from WorkflowJobBean w where w.endTimestamp"
099            + " < :endTime"),
100
101    @NamedQuery(name = "GET_COMPLETED_WORKFLOWS_WITH_NO_PARENT_OLDER_THAN", query = "select w.id from WorkflowJobBean w "
102            + "where w.endTimestamp < :endTime and w.parentId is null"),
103
104    @NamedQuery(name = "GET_COMPLETED_COORD_WORKFLOWS_OLDER_THAN", query = "select w.id, w.parentId from WorkflowJobBean w "
105            + "where w.endTimestamp < :endTime and w.parentId like '%C@%'"),
106
107    @NamedQuery(name = "GET_WORKFLOW", query = "select OBJECT(w) from WorkflowJobBean w where w.id = :id"),
108
109    @NamedQuery(name = "GET_WORKFLOW_STARTTIME", query = "select w.id, w.startTimestamp from WorkflowJobBean w where w.id = :id"),
110
111    @NamedQuery(name = "GET_WORKFLOW_START_END_TIME", query = "select w.id, w.startTimestamp, w.endTimestamp "
112            + "from WorkflowJobBean w where w.id = :id"),
113
114    @NamedQuery(name = "GET_WORKFLOW_USER_GROUP", query = "select w.user, w.group from WorkflowJobBean w where w.id = :id"),
115
116    @NamedQuery(name = "GET_WORKFLOW_SUSPEND", query = "select w.id, w.user, w.group, w.appName, w.statusStr, w.parentId,"
117            + " w.startTimestamp, w.endTimestamp, w.logToken, w.wfInstance  from WorkflowJobBean w where w.id = :id"),
118
119    @NamedQuery(name = "GET_WORKFLOW_RERUN", query = "select w.id, w.user, w.group, w.appName, w.statusStr, w.run, w.logToken,"
120            + " w.wfInstance, w.parentId from WorkflowJobBean w where w.id = :id"),
121
122    @NamedQuery(name = "GET_WORKFLOW_DEFINITION", query = "select w.id, w.user, w.group, w.appName, w.logToken, w.wfInstance "
123            + "from WorkflowJobBean w where w.id = :id"),
124
125    @NamedQuery(name = "GET_WORKFLOW_ACTION_OP", query = "select w.id, w.user, w.group, w.appName, w.appPath, w.statusStr, w.run,"
126            + " w.parentId, w.logToken, w.wfInstance, w.protoActionConf from WorkflowJobBean w where w.id = :id"),
127
128    @NamedQuery(name = "GET_WORKFLOW_KILL", query = "select w.id, w.user, w.group, w.appName, w.appPath, w.statusStr, w.parentId,"
129            + " w.startTimestamp, w.endTimestamp, w.logToken, w.wfInstance, w.slaXml, w.protoActionConf from WorkflowJobBean w"
130            + " where w.id = :id"),
131
132    @NamedQuery(name = "GET_WORKFLOW_RESUME", query = "select w.id, w.user, w.group, w.appName, w.appPath, w.statusStr,"
133            + " w.parentId, w.startTimestamp, w.endTimestamp, w.logToken, w.wfInstance, w.protoActionConf from WorkflowJobBean w "
134            + "where w.id = :id"),
135
136    @NamedQuery(name = "GET_WORKFLOW_FOR_UPDATE", query = "select OBJECT(w) from WorkflowJobBean w where w.id = :id"),
137
138    @NamedQuery(name = "GET_WORKFLOW_FOR_SLA", query = "select w.id, w.statusStr, w.startTimestamp, w.endTimestamp "
139            + "from WorkflowJobBean w where w.id = :id"),
140
141    @NamedQuery(name = "GET_WORKFLOW_ID_FOR_EXTERNAL_ID", query = "select  w.id from WorkflowJobBean w where w.externalId "
142            + "= :externalId"),
143
144    @NamedQuery(name = "GET_WORKFLOWS_COUNT_WITH_STATUS", query = "select count(w) from WorkflowJobBean w where w.statusStr "
145            + "= :status"),
146
147    @NamedQuery(name = "GET_WORKFLOWS_COUNT_WITH_STATUS_IN_LAST_N_SECS", query = "select count(w) from WorkflowJobBean w "
148            + "where w.statusStr = :status and w.lastModifiedTimestamp > :lastModTime"),
149
150    @NamedQuery(name = "GET_WORKFLOWS_WITH_WORKFLOW_PARENT_ID", query = "select w.id from WorkflowJobBean w where w.parentId "
151            + "= :parentId"),
152
153    @NamedQuery(name = "GET_WORKFLOWS_WITH_COORD_PARENT_ID", query = "select w.id from WorkflowJobBean w where w.parentId "
154            + "like :parentId"), // when setting parentId parameter, make sure to append a '%' (percent symbol) at the end
155    //(e.g. 0000004-130709155224435-oozie-rkan-C%")
156
157    @NamedQuery(name = "GET_WORKFLOWS_BASIC_INFO_BY_PARENT_ID", query = "select w.id, w.statusStr, w.endTimestamp,"
158            + " w.lastModifiedTimestamp from WorkflowJobBean w where w.parentId = :parentId"),
159
160    @NamedQuery(name = "GET_WORKFLOWS_BASIC_INFO_BY_COORD_PARENT_ID", query = "select w.id,  w.statusStr, w.endTimestamp,"
161            + " w.lastModifiedTimestamp from WorkflowJobBean w where w.parentId like :parentId"),
162
163    @NamedQuery(name = "GET_WORKFLOW_FOR_USER", query = "select w.user from WorkflowJobBean w where w.id = :id"),
164
165    @NamedQuery(name = "GET_WORKFLOW_STATUS", query = "select w.statusStr from WorkflowJobBean w where w.id = :id"),
166
167    @NamedQuery(name = "GET_WORKFLOWS_PARENT_COORD_RERUN", query = "select w.id, w.statusStr, w.startTimestamp, w.endTimestamp "
168            + "from WorkflowJobBean w where w.parentId = :parentId order by w.createdTimestamp")})
169@Table(name = "WF_JOBS")
170public class WorkflowJobBean implements Writable, WorkflowJob, JsonBean {
171
172    @Id
173    private String id;
174
175    @Basic
176    @Column(name = "proto_action_conf")
177    @Lob
178    @Strategy("org.apache.oozie.executor.jpa.StringBlobValueHandler")
179    private StringBlob protoActionConf;
180
181    @Basic
182    @Column(name = "log_token")
183    private String logToken = null;
184
185    @Basic
186    @Index
187    @Column(name = "external_id")
188    private String externalId = null;
189
190    @Basic
191    @Index
192    @Column(name = "status")
193    private String statusStr = WorkflowJob.Status.PREP.toString();
194
195    @Basic
196    @Index
197    @Column(name = "created_time")
198    private java.sql.Timestamp createdTimestamp = null;
199
200    @Basic
201    @Column(name = "start_time")
202    private java.sql.Timestamp startTimestamp = null;
203
204    @Basic
205    @Index
206    @Column(name = "end_time")
207    private java.sql.Timestamp endTimestamp = null;
208
209    @Basic
210    @Index
211    @Column(name = "last_modified_time")
212    private java.sql.Timestamp lastModifiedTimestamp = null;
213
214    @Basic
215    @Column(name = "wf_instance")
216    @Lob
217    @Strategy("org.apache.oozie.executor.jpa.BinaryBlobValueHandler")
218    private BinaryBlob wfInstance ;
219
220    @Basic
221    @Column(name = "sla_xml")
222    @Lob
223    @Strategy("org.apache.oozie.executor.jpa.StringBlobValueHandler")
224    private StringBlob slaXml;
225
226
227    @Basic
228    @Column(name = "app_name")
229    private String appName = null;
230
231    @Basic
232    @Column(name = "app_path")
233    private String appPath = null;
234
235    @Basic
236    @Column(name = "conf")
237    @Lob
238    @Strategy("org.apache.oozie.executor.jpa.StringBlobValueHandler")
239    private StringBlob conf;
240
241    @Basic
242    @Index
243    @Column(name = "user_name")
244    private String user = null;
245
246    @Basic
247    @Column(name = "group_name")
248    private String group;
249
250    @Basic
251    @Column(name = "run")
252    private int run = 1;
253
254    @Basic
255    @Index
256    @Column(name = "parent_id")
257    private String parentId;
258
259    @Transient
260    private String consoleUrl;
261
262    @Transient
263    private List<WorkflowActionBean> actions;
264
265
266    /**
267     * Default constructor.
268     */
269    public WorkflowJobBean() {
270        actions = new ArrayList<WorkflowActionBean>();
271    }
272
273    /**
274     * Serialize the workflow bean to a data output.
275     *
276     * @param dataOutput data output.
277     * @throws IOException thrown if the workflow bean could not be serialized.
278     */
279    public void write(DataOutput dataOutput) throws IOException {
280        WritableUtils.writeStr(dataOutput, getAppPath());
281        WritableUtils.writeStr(dataOutput, getAppName());
282        WritableUtils.writeStr(dataOutput, getId());
283        WritableUtils.writeStr(dataOutput, getParentId());
284        WritableUtils.writeStr(dataOutput, getConf());
285        WritableUtils.writeStr(dataOutput, getStatusStr());
286        dataOutput.writeLong((getCreatedTime() != null) ? getCreatedTime().getTime() : -1);
287        dataOutput.writeLong((getStartTime() != null) ? getStartTime().getTime() : -1);
288        dataOutput.writeLong((getLastModifiedTime() != null) ? getLastModifiedTime().getTime() : -1);
289        dataOutput.writeLong((getEndTime() != null) ? getEndTime().getTime() : -1);
290        WritableUtils.writeStr(dataOutput, getUser());
291        WritableUtils.writeStr(dataOutput, getGroup());
292        dataOutput.writeInt(getRun());
293        WritableUtils.writeStr(dataOutput, logToken);
294        WritableUtils.writeStr(dataOutput, getProtoActionConf());
295    }
296
297    /**
298     * Deserialize a workflow bean from a data input.
299     *
300     * @param dataInput data input.
301     * @throws IOException thrown if the workflow bean could not be deserialized.
302     */
303    public void readFields(DataInput dataInput) throws IOException {
304        setAppPath(WritableUtils.readStr(dataInput));
305        setAppName(WritableUtils.readStr(dataInput));
306        setId(WritableUtils.readStr(dataInput));
307        setParentId(WritableUtils.readStr(dataInput));
308        setConf(WritableUtils.readStr(dataInput));
309        setStatus(WorkflowJob.Status.valueOf(WritableUtils.readStr(dataInput)));
310        // setStatus(WritableUtils.readStr(dataInput));
311        long d = dataInput.readLong();
312        if (d != -1) {
313            setCreatedTime(new Date(d));
314        }
315        d = dataInput.readLong();
316        if (d != -1) {
317        }
318        setStartTime(new Date(d));
319        d = dataInput.readLong();
320        if (d != -1) {
321            setLastModifiedTime(new Date(d));
322        }
323        d = dataInput.readLong();
324        if (d != -1) {
325            setEndTime(new Date(d));
326        }
327        setUser(WritableUtils.readStr(dataInput));
328        setGroup(WritableUtils.readStr(dataInput));
329        setRun(dataInput.readInt());
330        logToken = WritableUtils.readStr(dataInput);
331        setProtoActionConf(WritableUtils.readStr(dataInput));
332        setExternalId(getExternalId());
333    }
334
335    public boolean inTerminalState() {
336        boolean inTerminalState = false;
337        switch (WorkflowJob.Status.valueOf(statusStr)) {
338            case FAILED:
339            case KILLED:
340            case SUCCEEDED:
341                inTerminalState = true;
342                break;
343            default:
344                break;
345        }
346        return inTerminalState;
347    }
348
349    public String getLogToken() {
350        return logToken;
351    }
352
353    public void setLogToken(String logToken) {
354        this.logToken = logToken;
355    }
356
357    public String getSlaXml() {
358        return slaXml == null ? null : slaXml.getString();
359    }
360
361    public void setSlaXml(String slaXml) {
362        if (this.slaXml == null) {
363            this.slaXml = new StringBlob(slaXml);
364        }
365        else {
366            this.slaXml.setString(slaXml);
367        }
368    }
369
370    public void setSlaXmlBlob(StringBlob slaXml) {
371        this.slaXml = slaXml;
372    }
373
374    public StringBlob getSlaXmlBlob() {
375        return this.slaXml;
376    }
377
378    public WorkflowInstance getWorkflowInstance() {
379        return wfInstance == null ? null : get(wfInstance.getBytes());
380    }
381
382    public BinaryBlob getWfInstanceBlob() {
383        return this.wfInstance;
384    }
385
386    public void setWorkflowInstance(WorkflowInstance workflowInstance) {
387        if (this.wfInstance == null) {
388            this.wfInstance = new BinaryBlob(WritableUtils.toByteArray((LiteWorkflowInstance) workflowInstance), true);
389        }
390        else {
391            this.wfInstance.setBytes(WritableUtils.toByteArray((LiteWorkflowInstance) workflowInstance));
392        }
393    }
394
395    public void setWfInstanceBlob(BinaryBlob wfInstance) {
396        this.wfInstance = wfInstance;
397    }
398
399    public String getProtoActionConf() {
400        return protoActionConf == null ? null : protoActionConf.getString();
401    }
402
403    public void setProtoActionConf(String protoActionConf) {
404        if (this.protoActionConf == null) {
405            this.protoActionConf = new StringBlob(protoActionConf);
406        }
407        else {
408            this.protoActionConf.setString(protoActionConf);
409        }
410    }
411
412    public void setProtoActionConfBlob (StringBlob protoBytes) {
413        this.protoActionConf = protoBytes;
414    }
415
416    public StringBlob getProtoActionConfBlob() {
417        return this.protoActionConf;
418    }
419
420    public String getlogToken() {
421        return logToken;
422    }
423
424    public Timestamp getLastModifiedTimestamp() {
425        return lastModifiedTimestamp;
426    }
427
428    public Timestamp getStartTimestamp() {
429        return startTimestamp;
430    }
431
432    public Timestamp getCreatedTimestamp() {
433        return createdTimestamp;
434    }
435
436    public Timestamp getEndTimestamp() {
437        return endTimestamp;
438    }
439
440    public void setStatusStr (String statusStr) {
441        this.statusStr = statusStr;
442    }
443
444    public void setStatus(Status val) {
445        this.statusStr = val.toString();
446    }
447
448    @Override
449    public Status getStatus() {
450        return Status.valueOf(statusStr);
451    }
452
453    public String getStatusStr() {
454        return statusStr;
455    }
456
457    public void setExternalId(String externalId) {
458        this.externalId = externalId;
459    }
460
461    @Override
462    public String getExternalId() {
463        return externalId;
464    }
465
466    public void setLastModifiedTime(Date lastModifiedTime) {
467        this.lastModifiedTimestamp = DateUtils.convertDateToTimestamp(lastModifiedTime);
468    }
469
470    public Date getLastModifiedTime() {
471        return DateUtils.toDate(lastModifiedTimestamp);
472    }
473
474    public Date getCreatedTime() {
475        return DateUtils.toDate(createdTimestamp);
476    }
477
478    public void setCreatedTime(Date createdTime) {
479        this.createdTimestamp = DateUtils.convertDateToTimestamp(createdTime);
480    }
481
482    @Override
483    public Date getStartTime() {
484        return DateUtils.toDate(startTimestamp);
485    }
486
487    public void setStartTime(Date startTime) {
488        this.startTimestamp = DateUtils.convertDateToTimestamp(startTime);
489    }
490
491    public Date getEndTime() {
492        return DateUtils.toDate(endTimestamp);
493    }
494
495    public void setEndTime(Date endTime) {
496        this.endTimestamp = DateUtils.convertDateToTimestamp(endTime);
497    }
498
499    private WorkflowInstance get(byte[] array) {
500        LiteWorkflowInstance pInstance = WritableUtils.fromByteArray(array, LiteWorkflowInstance.class);
501        return pInstance;
502    }
503
504    public JSONObject toJSONObject() {
505        return toJSONObject("GMT");
506    }
507
508    @SuppressWarnings("unchecked")
509    public JSONObject toJSONObject(String timeZoneId) {
510        JSONObject json = new JSONObject();
511        json.put(JsonTags.WORKFLOW_APP_PATH, getAppPath());
512        json.put(JsonTags.WORKFLOW_APP_NAME, getAppName());
513        json.put(JsonTags.WORKFLOW_ID, getId());
514        json.put(JsonTags.WORKFLOW_EXTERNAL_ID, getExternalId());
515        json.put(JsonTags.WORKFLOW_PARENT_ID, getParentId());
516        json.put(JsonTags.WORKFLOW_CONF, getConf());
517        json.put(JsonTags.WORKFLOW_STATUS, getStatus().toString());
518        json.put(JsonTags.WORKFLOW_LAST_MOD_TIME, JsonUtils.formatDateRfc822(getLastModifiedTime(), timeZoneId));
519        json.put(JsonTags.WORKFLOW_CREATED_TIME, JsonUtils.formatDateRfc822(getCreatedTime(), timeZoneId));
520        json.put(JsonTags.WORKFLOW_START_TIME, JsonUtils.formatDateRfc822(getStartTime(), timeZoneId));
521        json.put(JsonTags.WORKFLOW_END_TIME, JsonUtils.formatDateRfc822(getEndTime(), timeZoneId));
522        json.put(JsonTags.WORKFLOW_USER, getUser());
523        json.put(JsonTags.WORKFLOW_GROUP, getGroup());
524        json.put(JsonTags.WORKFLOW_ACL, getAcl());
525        json.put(JsonTags.WORKFLOW_RUN, (long) getRun());
526        json.put(JsonTags.WORKFLOW_CONSOLE_URL, getConsoleUrl());
527        json.put(JsonTags.WORKFLOW_ACTIONS, WorkflowActionBean.toJSONArray(actions, timeZoneId));
528        json.put(JsonTags.TO_STRING, toString());
529        return json;
530    }
531
532    public String getAppPath() {
533        return appPath;
534    }
535
536    public void setAppPath(String appPath) {
537        this.appPath = appPath;
538    }
539
540    public String getAppName() {
541        return appName;
542    }
543
544    public void setAppName(String appName) {
545        this.appName = appName;
546    }
547
548    public String getId() {
549        return id;
550    }
551
552    public void setId(String id) {
553        this.id = id;
554    }
555
556    public String getConf() {
557        return conf == null ? null : conf.getString();
558    }
559
560    public void setConf(String conf) {
561        if (this.conf == null) {
562            this.conf = new StringBlob(conf);
563        }
564        else {
565            this.conf.setString(conf);
566        }
567    }
568
569    public void setConfBlob(StringBlob conf) {
570        this.conf = conf;
571    }
572
573    public StringBlob getConfBlob() {
574        return this.conf;
575    }
576
577    public String getUser() {
578        return user;
579    }
580
581    public void setUser(String user) {
582        this.user = user;
583    }
584
585    public String getGroup() {
586        return group;
587    }
588
589    @Override
590    public String getAcl() {
591        return getGroup();
592    }
593
594    public void setGroup(String group) {
595        this.group = group;
596    }
597
598    public int getRun() {
599        return run;
600    }
601
602    public void setRun(int run) {
603        this.run = run;
604    }
605
606    /**
607     * Return the workflow job console URL.
608     *
609     * @return the workflow job console URL.
610     */
611    public String getConsoleUrl() {
612        return consoleUrl;
613    }
614
615    /**
616     * For a sub-workflow, return the Parent Workflow ID and for a top level workflow
617     * return the Coordinator action id, if any.
618     *
619     * @return the Parent Workflow Id/Coordinator Id if any.
620     */
621    public String getParentId() {
622        return parentId;
623    }
624
625    /**
626     * Set parent id for the workflow.
627     * For a top level workflow it is the coordinator action id if submitted through coordinator
628     *
629     * @param parentId the Parent Action id
630     */
631    public void setParentId(String parentId) {
632        this.parentId = parentId;
633    }
634
635    /**
636     * Set the workflow job console URL.
637     *
638     * @param consoleUrl the workflow job console URL.
639     */
640    public void setConsoleUrl(String consoleUrl) {
641        this.consoleUrl = consoleUrl;
642    }
643
644    @SuppressWarnings("unchecked")
645    public List<WorkflowAction> getActions() {
646        return (List) actions;
647    }
648
649    public void setActions(List<WorkflowActionBean> nodes) {
650        this.actions = (nodes != null) ? nodes : new ArrayList<WorkflowActionBean>();
651    }
652
653    @Override
654    public String toString() {
655        return MessageFormat.format("Workflow id[{0}] status[{1}]", getId(), getStatus());
656    }
657
658    /**
659     * Convert a workflows list into a JSONArray.
660     *
661     * @param workflows workflows list.
662     * @param timeZoneId time zone to use for dates in the JSON array.
663     * @return the corresponding JSON array.
664     */
665    @SuppressWarnings("unchecked")
666    public static JSONArray toJSONArray(List<WorkflowJobBean> workflows, String timeZoneId) {
667        JSONArray array = new JSONArray();
668        if (workflows != null) {
669            for (WorkflowJobBean node : workflows) {
670                array.add(node.toJSONObject(timeZoneId));
671            }
672        }
673        return array;
674    }
675
676
677
678}