AT&T 2.0.19 Code drop, stage 3
[aaf/authz.git] / auth / auth-gui / src / main / java / org / onap / aaf / auth / gui / pages / ApprovalForm.java
1 /**
2  * ============LICENSE_START====================================================
3  * org.onap.aaf
4  * ===========================================================================
5  * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
6  * ===========================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * 
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  * 
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END====================================================
19  *
20  */
21
22 package org.onap.aaf.auth.gui.pages;
23
24 import java.io.IOException;
25 import java.net.ConnectException;
26 import java.util.ArrayList;
27 import java.util.Collections;
28 import java.util.Comparator;
29 import java.util.List;
30
31 import org.onap.aaf.auth.env.AuthzEnv;
32 import org.onap.aaf.auth.env.AuthzTrans;
33 import org.onap.aaf.auth.gui.AAF_GUI;
34 import org.onap.aaf.auth.gui.BreadCrumbs;
35 import org.onap.aaf.auth.gui.Form;
36 import org.onap.aaf.auth.gui.NamedCode;
37 import org.onap.aaf.auth.gui.Page;
38 import org.onap.aaf.auth.gui.Table;
39 import org.onap.aaf.auth.gui.Table.Cells;
40 import org.onap.aaf.auth.gui.table.AbsCell;
41 import org.onap.aaf.auth.gui.table.ButtonCell;
42 import org.onap.aaf.auth.gui.table.RadioCell;
43 import org.onap.aaf.auth.gui.table.RefCell;
44 import org.onap.aaf.auth.gui.table.TableData;
45 import org.onap.aaf.auth.gui.table.TextAndRefCell;
46 import org.onap.aaf.auth.gui.table.TextCell;
47 import org.onap.aaf.auth.org.Organization;
48 import org.onap.aaf.auth.org.OrganizationFactory;
49 import org.onap.aaf.auth.org.Organization.Identity;
50 import org.onap.aaf.cadi.CadiException;
51 import org.onap.aaf.cadi.client.Future;
52 import org.onap.aaf.cadi.client.Rcli;
53 import org.onap.aaf.cadi.client.Retryable;
54 import org.onap.aaf.misc.env.APIException;
55 import org.onap.aaf.misc.env.Env;
56 import org.onap.aaf.misc.env.Slot;
57 import org.onap.aaf.misc.env.TimeTaken;
58 import org.onap.aaf.misc.xgen.Cache;
59 import org.onap.aaf.misc.xgen.DynamicCode;
60 import org.onap.aaf.misc.xgen.Mark;
61 import org.onap.aaf.misc.xgen.html.HTMLGen;
62
63 import aaf.v2_0.Approval;
64 import aaf.v2_0.Approvals;
65
66 public class ApprovalForm extends Page {
67         // Package on purpose
68         static final String NAME="Approvals";
69         static final String HREF = "/gui/approve";
70         static final String[] FIELDS = new String[] {"line[]","user"};
71         
72         
73         public ApprovalForm(final AAF_GUI gui, final Page ... breadcrumbs) throws APIException, IOException {
74                 super(gui.env,NAME,HREF, FIELDS,
75
76                         new BreadCrumbs(breadcrumbs),
77                         new NamedCode(false, "filterByUser") {
78                                 @Override
79                                 public void code(final Cache<HTMLGen> cache, final HTMLGen hgen) throws APIException, IOException {
80                                         cache.dynamic(hgen, new DynamicCode<HTMLGen, AAF_GUI, AuthzTrans>() {
81                                                 @Override
82                                                 public void code(final AAF_GUI gui, final AuthzTrans trans,     final Cache<HTMLGen> cache, final HTMLGen hgen) throws APIException, IOException {
83                                                         String user = trans.get(trans.env().slot(NAME+".user"),"");
84                                                         hgen.incr("p", "class=userFilter")
85                                                                 .text("Filter by User:")
86                                                                 .tagOnly("input", "type=text", "value="+user, "id=userTextBox")
87                                                                 .tagOnly("input", "type=button", "onclick=userFilter('"+HREF+"');", "value=Go!")
88                                                                 .end();
89                                                                 }
90                                         });
91                                 }
92                         },
93                         new Form(true,new Table<AAF_GUI,AuthzTrans>("Approval Requests", gui.env.newTransNoAvg(),new Model(gui.env),"class=stdform"))
94                                 .preamble("The following requires your Approval to proceed in the AAF System.</p><p class=subtext>Hover on Identity for Name; click for WebPhone; If Deny is the only option, User is no longer valid."),
95                         new NamedCode(false, "selectAlljs") {
96                                 @Override
97                                 public void code(final Cache<HTMLGen> cache, final HTMLGen hgen) throws APIException, IOException {
98                                         Mark jsStart = new Mark();
99                                         hgen.js(jsStart);
100                                         hgen.text("function selectAll(radioClass) {");
101                                         hgen.text("var radios = document.querySelectorAll(\".\"+radioClass);");
102                                         hgen.text("for (i = 0; i < radios.length; i++) {");
103                                         hgen.text("radios[i].checked = true;");
104                                         hgen.text("}");
105                                         hgen.text("}");
106                                         hgen.end(jsStart);
107                                 }
108                         });
109                 
110         }
111         
112         /**
113          * Implement the Table Content for Approvals
114          * 
115          * @author Jonathan
116          *
117          */
118         private static class Model extends TableData<AAF_GUI,AuthzTrans> {
119                 //TODO come up with a generic way to do ILM Info (people page)
120                 private static final String TODO_ILM_INFO = "TODO: ILM Info";
121                 private static final String DOMAIN_OF_USER = "@DOMAIN";
122                 
123                 private static final String[] headers = new String[] {"Identity","Request","Approve","Deny"};
124                 private Slot sUser;
125                 
126                 public Model(AuthzEnv env) {
127                         sUser = env.slot(NAME+".user");
128                 }
129                 
130                 @Override
131                 public String[] headers() {
132                         return headers;
133                 }
134                 
135                 @Override
136                 public Cells get(final AuthzTrans trans, final AAF_GUI gui) {
137                         final String userParam = trans.get(sUser, null);
138                         ArrayList<AbsCell[]> rv = new ArrayList<AbsCell[]>();
139                         String msg = null;
140                         TimeTaken tt = trans.start("AAF Get Approvals for Approver",Env.REMOTE);
141                         try {
142                                 final List<Approval> pendingApprovals = new ArrayList<Approval>();
143                                 final List<Integer> beginIndicesPerApprover = new ArrayList<Integer>();
144                                 int numLeft = gui.clientAsUser(trans.getUserPrincipal(), new Retryable<Integer>() {
145                                         @Override
146                                         public Integer code(Rcli<?> client) throws CadiException, ConnectException, APIException {
147                                                 Future<Approvals> fa = client.read("/authz/approval/approver/"+trans.user(),gui.getDF(Approvals.class));
148                                                 int numLeft = 0;
149                                                 if(fa.get(AAF_GUI.TIMEOUT)) {
150                                                         
151                                                         if(fa.value!=null) {
152                                                                 for (Approval appr : fa.value.getApprovals()) {
153                                                                         if (appr.getStatus().equals("pending")) {
154                                                                                 if (userParam!=null) {
155                                                                                         if (!appr.getUser().equalsIgnoreCase(userParam)) {
156                                                                                                 numLeft++;
157                                                                                                 continue;
158                                                                                         }
159                                                                                 }
160                                                                                 pendingApprovals.add(appr);
161                                                                         }
162                                                                 }
163                                                         }
164                                                         
165                                                         String prevApprover = null;
166                                                         int overallIndex = 0;
167                                                                 
168                                                         for (Approval appr : pendingApprovals) {
169                                                                 String currApprover = appr.getApprover();
170                                                                 if (!currApprover.equals(prevApprover)) {
171                                                                         prevApprover = currApprover;
172                                                                         beginIndicesPerApprover.add(overallIndex);
173                                                                 }
174                                                                 overallIndex++;
175                                                         }
176                                                 }
177                                                 return numLeft;
178                                         }
179                                 });
180                                 
181                                 if (pendingApprovals.size() > 0) {
182                                         // Only add select all links if we have approvals
183                                         AbsCell[] selectAllRow = new AbsCell[] {
184                                                         AbsCell.Null,
185                                                         AbsCell.Null,
186                                                         new ButtonCell("all", "onclick=selectAll('approve')", "class=selectAllButton"),
187                                                         new ButtonCell("all", "onclick=selectAll('deny')", "class=selectAllButton")
188                                                 };
189                                         rv.add(selectAllRow);
190                                 }
191                                                 
192                                 int line=-1;
193                                 
194                                 while (beginIndicesPerApprover.size() > 0) {
195                                         int beginIndex = beginIndicesPerApprover.remove(0);
196                                         int endIndex = (beginIndicesPerApprover.isEmpty()?pendingApprovals.size():beginIndicesPerApprover.get(0));
197                                         List<Approval> currApproverList = pendingApprovals.subList(beginIndex, endIndex);
198                                         
199                                         String currApproverFull = currApproverList.get(0).getApprover();
200                                         String currApproverShort = currApproverFull.substring(0,currApproverFull.indexOf('@'));
201                                         String currApprover = (trans.user().indexOf('@')<0?currApproverShort:currApproverFull);
202                                         if (!currApprover.equals(trans.user())) {
203                                                 AbsCell[] approverHeader;
204                                                 if (currApproverFull.substring(currApproverFull.indexOf('@')).equals(DOMAIN_OF_USER)) {
205                                                         approverHeader = new AbsCell[] { 
206                                                                         new TextAndRefCell("Approvals Delegated to Me by ", currApprover,
207                                                                                         TODO_ILM_INFO + currApproverShort, 
208                                                                                         true,
209                                                                                         new String[] {"colspan=4", "class=head"})
210                                                         };
211                                                 } else {
212                                                         approverHeader = new AbsCell[] { 
213                                                                         new TextCell("Approvals Delegated to Me by " + currApprover,
214                                                                                         new String[] {"colspan=4", "class=head"})
215                                                         };
216                                                 }
217                                                 rv.add(approverHeader);
218                                         }
219                                         
220                                         // Sort by User Requesting
221                                         Collections.sort(currApproverList, new Comparator<Approval>() {
222                                                 @Override
223                                                 public int compare(Approval a1, Approval a2) {
224                                                         return a1.getUser().compareTo(a2.getUser());
225                                                 }
226                                         });
227                                         
228                                         String prevUser = null;
229                                         boolean userOK=true;
230
231                                         for (Approval appr : currApproverList) {
232                                                 if(++line<MAX_LINE) { // limit number displayed at one time.
233                                                         AbsCell userCell;
234                                                         String user = appr.getUser();
235                                                         if(user.equals(prevUser)) {
236                                                                 userCell = AbsCell.Null; 
237                                                         } else if (user.endsWith(DOMAIN_OF_USER)){
238                                                                 userOK=true;
239                                                                 String title;
240                                                                 Organization org = OrganizationFactory.obtain(trans.env(), user);
241                                                                 if(org==null) {
242                                                                         title="";
243                                                                 } else {
244                                                                         Identity au = org.getIdentity(trans, user);
245                                                                         if(au!=null) {
246                                                                                 if(au.type().equals("MECHID")) {
247                                                                                         Identity managedBy = au.responsibleTo();
248                                                                                         if(managedBy==null) {
249                                                                                                 title ="title=" + au.type();
250                                                                                         } else {
251                                                                                                 title="title=Sponsor is " + managedBy.fullName();                                                                                               
252                                                                                         }
253                                                                                 } else {
254                                                                                         title="title=" + au.fullName();
255                                                                                 }
256                                                                         } else {
257                                                                                 userOK=false;
258                                                                                 title="title=Not a User at " + org.getName();
259                                                                         }
260                                                                 }
261                                                                 userCell = new RefCell(prevUser=user, 
262                                                                         TODO_ILM_INFO+user.substring(0, user.length()-DOMAIN_OF_USER.length()),
263                                                                         true,
264                                                                         title);
265                                                         } else {
266                                                                 userCell = new TextCell(prevUser=user);
267                                                         }
268                                                         AbsCell[] sa = new AbsCell[] {
269                                                                 userCell,
270                                                                 new TextCell(appr.getMemo()),
271                                                                 userOK?new RadioCell("line."+ line,"approve", "approved|"+appr.getTicket()):new TextCell(""),
272                                                                 new RadioCell("line."+ line,"deny", "denied|"+appr.getTicket())
273                                                         };
274                                                         rv.add(sa);
275                                                 } else {
276                                                         ++numLeft;
277                                                 }
278                                         }
279                                 }
280                                 if(numLeft>0) {
281                                         msg = "After these, there will be " + numLeft + " approvals left to process";
282                                 }
283                                 if(rv.size()==0) {
284                                         if (numLeft>0) {
285                                                 msg = "No Approvals to process at this time for user " + userParam +". You have " 
286                                                         + numLeft + " other approvals to process.";
287                                         } else {
288                                                 msg = "No Approvals to process at this time";
289                                         }
290                                 }
291                         } catch (Exception e) {
292                                 trans.error().log(e);
293                         } finally {
294                                 tt.done();
295                         }
296                 return new Cells(rv,msg);
297                 }
298         }
299 }