001    /**
002     * Copyright 2005-2012 The Kuali Foundation
003     *
004     * Licensed under the Educational Community License, Version 2.0 (the "License");
005     * you may not use this file except in compliance with the License.
006     * You may obtain a copy of the License at
007     *
008     * http://www.opensource.org/licenses/ecl2.php
009     *
010     * Unless required by applicable law or agreed to in writing, software
011     * distributed under the License is distributed on an "AS IS" BASIS,
012     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013     * See the License for the specific language governing permissions and
014     * limitations under the License.
015     */
016    package org.kuali.rice.edl.impl.components;
017    
018    import org.apache.commons.fileupload.FileItem;
019    import org.apache.commons.lang.StringUtils;
020    import org.apache.log4j.Logger;
021    import org.kuali.rice.core.api.CoreApiServiceLocator;
022    import org.kuali.rice.core.api.config.property.ConfigContext;
023    import org.kuali.rice.core.api.mail.EmailBcList;
024    import org.kuali.rice.core.api.mail.EmailBody;
025    import org.kuali.rice.core.api.mail.EmailCcList;
026    import org.kuali.rice.core.api.mail.EmailContent;
027    import org.kuali.rice.core.api.mail.EmailFrom;
028    import org.kuali.rice.core.api.mail.EmailSubject;
029    import org.kuali.rice.core.api.mail.EmailToList;
030    import org.kuali.rice.core.api.util.RiceConstants;
031    import org.kuali.rice.core.api.util.xml.XmlHelper;
032    import org.kuali.rice.core.api.util.xml.XmlJotter;
033    import org.kuali.rice.coreservice.api.CoreServiceApiServiceLocator;
034    import org.kuali.rice.coreservice.framework.CoreFrameworkServiceLocator;
035    import org.kuali.rice.edl.impl.EDLContext;
036    import org.kuali.rice.edl.impl.EDLModelComponent;
037    import org.kuali.rice.edl.impl.EDLXmlUtils;
038    import org.kuali.rice.edl.impl.RequestParser;
039    import org.kuali.rice.edl.impl.service.EdlServiceLocator;
040    import org.kuali.rice.kew.api.KewApiConstants;
041    import org.kuali.rice.kew.api.WorkflowDocument;
042    import org.kuali.rice.kew.api.WorkflowRuntimeException;
043    import org.kuali.rice.kew.mail.EmailStyleHelper;
044    import org.kuali.rice.kew.notes.Attachment;
045    import org.kuali.rice.kew.notes.CustomNoteAttribute;
046    import org.kuali.rice.kew.notes.Note;
047    import org.kuali.rice.kew.notes.service.NoteService;
048    import org.kuali.rice.kew.routeheader.DocumentRouteHeaderValue;
049    import org.kuali.rice.kew.routeheader.service.RouteHeaderService;
050    import org.kuali.rice.kew.service.KEWServiceLocator;
051    import org.kuali.rice.kim.api.identity.Person;
052    import org.kuali.rice.kim.api.services.KimApiServiceLocator;
053    import org.w3c.dom.Document;
054    import org.w3c.dom.Element;
055    
056    import javax.xml.bind.JAXBContext;
057    import javax.xml.bind.Marshaller;
058    import javax.xml.parsers.DocumentBuilder;
059    import javax.xml.parsers.DocumentBuilderFactory;
060    import javax.xml.transform.Templates;
061    import javax.xml.transform.TransformerConfigurationException;
062    import javax.xml.xpath.XPath;
063    import javax.xml.xpath.XPathConstants;
064    import javax.xml.xpath.XPathExpressionException;
065    import javax.xml.xpath.XPathFactory;
066    import java.sql.Timestamp;
067    import java.text.DateFormat;
068    import java.util.ArrayList;
069    import java.util.Collections;
070    import java.util.Comparator;
071    import java.util.Date;
072    import java.util.Iterator;
073    import java.util.List;
074    import java.util.StringTokenizer;
075    import java.util.regex.Matcher;
076    import java.util.regex.Pattern;
077    
078    /**
079     * Adds notes support to EDL
080     * 
081     * @author Kuali Rice Team (rice.collab@kuali.org)
082     * 
083     */
084    public class NoteConfigComponent implements EDLModelComponent {
085    
086        private static final Logger LOG = Logger.getLogger(NoteConfigComponent.class);
087    
088        private EmailStyleHelper emailStyleHelper = new EmailStyleHelper();
089        private String styleName;
090        private String from;
091        private List<String> to;
092        private List<String> cc = new ArrayList<String>();
093        private List<String> bc = new ArrayList<String>();
094        private static final String DEFAULT_EMAIL_FROM_ADDRESS = CoreFrameworkServiceLocator.getParameterService()
095                .getParameterValueAsString(KewApiConstants.KEW_NAMESPACE, "Mailer", "FROM_ADDRESS");//"workflow@indiana.edu";
096    
097        public void updateDOM(Document dom, Element configElement, EDLContext edlContext) {
098            NoteForm noteForm = new NoteForm(edlContext.getRequestParser());
099            WorkflowDocument document = (WorkflowDocument) edlContext.getRequestParser().getAttribute(
100                    RequestParser.WORKFLOW_DOCUMENT_SESSION_KEY);
101            try {
102                //establish notes depends on a document id being set on noteform or nothing happens
103                if (document != null) {
104                    noteForm.setDocId(document.getDocumentId());
105                }
106                establishNotes(noteForm, edlContext, dom);
107                addNotes(dom, noteForm);
108            } catch (Exception e) {
109                throw new WorkflowRuntimeException("Caught exception processing notes", e);
110            }
111    
112        }
113    
114        public void establishNotes(NoteForm form, EDLContext edlContext, Document dom) throws Exception {
115    
116            form.setCurrentUserName(edlContext.getUserSession().getPerson().getName());
117            form.setCurrentDate(getCurrentDate());
118            String methodToCall = form.getMethodToCall();
119            if (!org.apache.commons.lang.StringUtils.isEmpty(methodToCall)) {
120                if ("save".equalsIgnoreCase(methodToCall)) {
121                    this.saveNote(form, edlContext, dom);
122                } else if ("edit".equalsIgnoreCase(methodToCall)) {
123                    this.editNote(form);
124                } else if ("add".equalsIgnoreCase(methodToCall)) {
125                    this.addNote(form);
126                } else if ("cancel".equalsIgnoreCase(methodToCall)) {
127                    this.cancelEdit(form);
128                } else if ("delete".equalsIgnoreCase(methodToCall)) {
129                    this.deleteNote(form);
130                } else if ("sort".equalsIgnoreCase(methodToCall)) {
131                    this.sortNotes(form);
132                } else if ("deleteAttachment".equalsIgnoreCase(methodToCall)) {
133                    this.deleteAttachment(form);
134                }
135            }
136            retrieveNoteList(form, edlContext);
137    
138        }
139    
140        /**
141         * Method added for notes editing function. Retrieve Note Listing from Route Header and put that
142         * in EdocLiteForm.
143         * @param request
144         * @param noteForm
145         * @throws Exception
146         */
147    
148        private void retrieveNoteList(NoteForm form, EDLContext edlContext) throws Exception {
149            if (form.getDocId() != null) {
150                List allNotes = getNoteService().getNotesByDocumentId(form.getDocId());
151                CustomNoteAttribute customNoteAttribute = null;
152                DocumentRouteHeaderValue routeHeader = getRouteHeaderService().getRouteHeader(form.getDocId());
153                boolean canAddNotes = false;
154                if (routeHeader != null) {
155                    customNoteAttribute = routeHeader.getCustomNoteAttribute();
156                    if (customNoteAttribute != null) {
157                        customNoteAttribute.setUserSession(edlContext.getUserSession());
158                        canAddNotes = customNoteAttribute.isAuthorizedToAddNotes();
159                    }
160                }
161                Iterator notesIter = allNotes.iterator();
162                while (notesIter.hasNext()) {
163                    Note singleNote = (Note) notesIter.next();
164                    singleNote.setNoteCreateLongDate(new Long(singleNote.getNoteCreateDate().getTime()));
165                    getAuthorData(singleNote);
166                    boolean canEditNote = false;
167                    if (customNoteAttribute != null) {
168                        canEditNote = customNoteAttribute.isAuthorizedToEditNote(singleNote);
169                    }
170                    singleNote.setAuthorizedToEdit(Boolean.valueOf(canEditNote));
171                    if (form.getNoteIdNumber() != null
172                            && (StringUtils.equals(form.getNoteIdNumber(), singleNote.getNoteId()))) {
173                        singleNote.setEditingNote(Boolean.TRUE);
174                    }
175                }
176                if (form.getSortNotes() != null && form.getSortNotes().booleanValue()) {
177                    if (KewApiConstants.Sorting.SORT_SEQUENCE_DSC.equalsIgnoreCase(form.getSortOrder())) {
178                        form.setSortOrder(KewApiConstants.Sorting.SORT_SEQUENCE_ASC);
179                        form.setSortNotes(Boolean.FALSE);
180                    } else {
181                        form.setSortOrder(KewApiConstants.Sorting.SORT_SEQUENCE_DSC);
182                        form.setSortNotes(Boolean.FALSE);
183                    }
184                } else {
185                    form.setSortOrder(form.getSortOrder());
186                }
187                form.setNoteList(sortNotes(allNotes, form.getSortOrder()));
188                form.setNumberOfNotes(new Integer(allNotes.size()));
189                form.setAuthorizedToAdd(new Boolean(canAddNotes));
190                form.setShowAdd(Boolean.TRUE);
191                if (!canAddNotes) {
192                    form.setShowAdd(Boolean.FALSE);
193                } else if (form.getNoteList().size() == 0) {
194                    //form.setShowAdd(Boolean.TRUE);
195                }
196            }
197        }
198    
199        public void editNote(NoteForm form) throws Exception {
200            form.setShowEdit("yes");
201            // Note noteToEdit =
202            // getNoteService().getNoteByNoteId(form.getNoteIdNumber());
203            //form.setNote(noteToEdit);
204            form.getNote().setNoteCreateLongDate(new Long(form.getNote().getNoteCreateDate().getTime()));
205            form.getNote().setNoteText(form.getNoteText());
206            //retrieveNoteList(request, form);
207        }
208    
209        public void addNote(NoteForm form) throws Exception {
210            form.setShowEdit("no");
211            form.setNoteIdNumber(null);
212            form.setShowAdd(Boolean.TRUE);
213            //retrieveNoteList(request,form);
214    
215        }
216    
217        public void cancelEdit(NoteForm form) throws Exception {
218            form.setShowEdit("no");
219            form.setNote(new Note());
220            form.setNoteIdNumber(null);
221            //retrieveNoteList(request, form);
222        }
223    
224        public void deleteNote(NoteForm form) throws Exception {
225            Note noteToDelete = getNoteService().getNoteByNoteId(form.getNoteIdNumber());
226            getNoteService().deleteNote(noteToDelete);
227            form.setShowEdit("no");
228            //retrieveNoteList(request, form);
229            form.setNote(new Note());
230            form.setNoteIdNumber(null);
231        }
232    
233        public void sortNotes(NoteForm form) throws Exception {
234            form.setShowEdit("no");
235        }
236    
237        public void deleteAttachment(NoteForm form) throws Exception {
238            Note note = getNoteService().getNoteByNoteId(form.getNoteIdNumber());
239            getNoteService().deleteAttachment((Attachment) note.getAttachments().remove(0));
240        }
241    
242        public void saveNote(NoteForm form, EDLContext edlContext, Document dom) throws Exception {
243            Note noteToSave = null;
244            if (form.getShowEdit() != null && form.getShowEdit().equals("yes")) {
245                //LOG.debug(form.getNoteIdNumber());
246                noteToSave = getNoteService().getNoteByNoteId(form.getNoteIdNumber());
247                String noteText = form.getNoteText();
248                if (noteText != null) {
249                    noteToSave.setNoteText(noteText);
250                }
251                //LOG.debug(noteToSave);
252                //LOG.debug(noteToSave.getNoteCreateDate());
253                //noteToSave.setNoteCreateDate(new Timestamp(noteToSave.getNoteCreateLongDate().longValue()));
254            } else {
255                noteToSave = new Note();
256                noteToSave.setNoteId(null);
257                noteToSave.setDocumentId(form.getDocId());
258                noteToSave.setNoteCreateDate(new Timestamp((new Date()).getTime()));
259                noteToSave.setNoteAuthorWorkflowId(edlContext.getUserSession().getPrincipalId());
260                noteToSave.setNoteText(form.getAddText());
261            }
262            CustomNoteAttribute customNoteAttribute = null;
263            DocumentRouteHeaderValue routeHeader = getRouteHeaderService().getRouteHeader(noteToSave.getDocumentId());
264            boolean canEditNote = false;
265            boolean canAddNotes = false;
266            if (routeHeader != null) {
267                customNoteAttribute = routeHeader.getCustomNoteAttribute();
268                if (customNoteAttribute != null) {
269                    customNoteAttribute.setUserSession(edlContext.getUserSession());
270                    canAddNotes = customNoteAttribute.isAuthorizedToAddNotes();
271                    canEditNote = customNoteAttribute.isAuthorizedToEditNote(noteToSave);
272                }
273            }
274            if ((form.getShowEdit() != null && form.getShowEdit().equals("yes") && canEditNote) ||
275                    ((form.getShowEdit() == null || !form.getShowEdit().equals("yes")) && canAddNotes)) {
276                FileItem uploadedFile = (FileItem) form.getFile();
277                if (uploadedFile != null && org.apache.commons.lang.StringUtils.isNotBlank(uploadedFile.getName())) {
278                    Attachment attachment = new Attachment();
279                    attachment.setAttachedObject(uploadedFile.getInputStream());
280                    String internalFileIndicator = uploadedFile.getName();
281                    int indexOfSlash = internalFileIndicator.lastIndexOf("/");
282                    int indexOfBackSlash = internalFileIndicator.lastIndexOf("\\");
283                    if (indexOfSlash >= 0) {
284                        internalFileIndicator = internalFileIndicator.substring(indexOfSlash + 1);
285                    } else {
286                        if (indexOfBackSlash >= 0) {
287                            internalFileIndicator = internalFileIndicator.substring(indexOfBackSlash + 1);
288                        }
289                    }
290                    attachment.setFileName(internalFileIndicator);
291                    LOG.debug(internalFileIndicator);
292                    attachment.setMimeType(uploadedFile.getContentType());
293                    attachment.setNote(noteToSave);
294                    noteToSave.getAttachments().add(attachment);
295                }
296                if (org.apache.commons.lang.StringUtils.isEmpty(noteToSave.getNoteText())
297                        && noteToSave.getAttachments().size() == 0) {
298                    if (form.getShowEdit() != null && form.getShowEdit().equals("yes")) {
299                        form.setNote(new Note());
300                    } else {
301                        form.setAddText(null);
302                    }
303                    form.setShowEdit("no");
304                    form.setNoteIdNumber(null);
305                    //                      throw new Exception("Note has empty content");
306                    EDLXmlUtils.addGlobalErrorMessage(dom, "Note has empty content");
307                    return;
308                }
309                getNoteService().saveNote(noteToSave);
310    
311                // add ability to send emails when a note is saved. 
312                boolean sendEmailOnNoteSave = false;
313                // Check if edoclite specifies <param name="sendEmailOnNoteSave">
314                Document edlDom = EdlServiceLocator.getEDocLiteService()
315                        .getDefinitionXml(edlContext.getEdocLiteAssociation());
316                XPath xpath = XPathFactory.newInstance().newXPath();
317                String xpathExpression = "//config/param[@name='sendEmailOnNoteSave']";
318                try {
319                    String match = (String) xpath.evaluate(xpathExpression, edlDom, XPathConstants.STRING);
320                    if (!StringUtils.isBlank(match) && match.equals("true")) {
321                        sendEmailOnNoteSave = true;
322                    }
323                } catch (XPathExpressionException e) {
324                    throw new WorkflowRuntimeException(
325                            "Unable to evaluate sendEmailOnNoteSave xpath expression in NoteConfigComponent saveNote method"
326                                    + xpathExpression, e);
327                }
328    
329                if (sendEmailOnNoteSave) {
330                    xpathExpression = "//data/version[@current='true']/field[@name='emailTo']/value";
331                    String emailTo = xpath.evaluate(xpathExpression, dom);
332                    if (StringUtils.isBlank(emailTo)) {
333                        EDLXmlUtils.addGlobalErrorMessage(dom,
334                                "No email notifications were sent because EmailTo field was empty.");
335                        return;
336                    }
337                    // Actually send the emails.
338                    if (isProduction()) {
339                        this.to = stringToList(emailTo);
340                    } else {
341                        String testAddress = getTestAddress(edlDom);
342                        if (StringUtils.isBlank(testAddress)) {
343                            EDLXmlUtils
344                                    .addGlobalErrorMessage(
345                                            dom,
346                                            "No email notifications were sent because testAddress edl param was empty or not specified in a non production environment");
347                            return;
348                        }
349                        this.to = stringToList(getTestAddress(edlDom));
350                    }
351                    if (!isEmailListValid(this.to)) {
352                        EDLXmlUtils
353                                .addGlobalErrorMessage(
354                                        dom,
355                                        "No email notifications were sent because emailTo field contains invalid email address.");
356                        return;
357                    }
358                    String noteEmailStylesheet = "";
359                    xpathExpression = "//config/param[@name='noteEmailStylesheet']";
360                    try {
361                        noteEmailStylesheet = (String) xpath.evaluate(
362                                xpathExpression, edlDom, XPathConstants.STRING);
363                        if (StringUtils.isBlank(noteEmailStylesheet)) {
364                            EDLXmlUtils
365                                    .addGlobalErrorMessage(
366                                            dom,
367                                            "No email notifications were sent because noteEmailStylesheet edl param was empty or not specified.");
368                            return;
369                        }
370                    } catch (XPathExpressionException e) {
371                        throw new WorkflowRuntimeException(
372                                "Unable to evaluate noteEmailStylesheet xpath expression in NoteConfigComponent method"
373                                        + xpathExpression, e);
374                    }
375                    this.styleName = noteEmailStylesheet;
376                    this.from = DEFAULT_EMAIL_FROM_ADDRESS;
377                    Document document = generateXmlInput(form, edlContext, edlDom);
378                    if (LOG.isDebugEnabled()) {
379                        LOG.debug("XML input for email tranformation:\n" + XmlJotter.jotNode(document));
380                    }
381                    Templates style = loadStyleSheet(styleName);
382                    EmailContent emailContent = emailStyleHelper
383                            .generateEmailContent(style, document);
384                    if (!this.to.isEmpty()) {
385                        CoreApiServiceLocator.getMailer().sendEmail(
386                                new EmailFrom(from), new EmailToList(this.to),
387                                new EmailSubject(emailContent.getSubject()),
388                                new EmailBody(emailContent.getBody()),
389                                new EmailCcList(this.cc), new EmailBcList(this.bc),
390                                emailContent.isHtml());
391                    }
392                }
393    
394            }
395            if (form.getShowEdit() != null && form.getShowEdit().equals("yes")) {
396                form.setNote(new Note());
397            } else {
398                form.setAddText(null);
399            }
400            form.setShowEdit("no");
401            form.setNoteIdNumber(null);
402        }
403    
404        protected String getTestAddress(Document edlDom) {
405            String testAddress = "";
406            XPath xpath = XPathFactory.newInstance().newXPath();
407            String xpathExpression = "//config/param[@name='testAddress']";
408            try {
409                testAddress = (String) xpath.evaluate(xpathExpression, edlDom, XPathConstants.STRING);
410            } catch (XPathExpressionException e) {
411                throw new WorkflowRuntimeException(
412                        "Unable to evaluate testAddressAttributeFound xpath expression in NoteConfigComponent getTestAddress method"
413                                + xpathExpression, e);
414            }
415            return testAddress;
416        }
417    
418        protected Document generateXmlInput(NoteForm form, EDLContext edlContext, Document dom) throws Exception {
419            DocumentBuilder db = getDocumentBuilder(true);
420            Document doc = db.newDocument();
421            Element emailNodeElem = doc.createElement("emailNode");
422            doc.appendChild(emailNodeElem);
423            WorkflowDocument document = (WorkflowDocument) edlContext.getRequestParser().getAttribute(
424                    RequestParser.WORKFLOW_DOCUMENT_SESSION_KEY);
425    
426            /* Upgrade Changes 0914 to 1011 */
427            //RouteHeaderVO routeHeaderVO = document.getRouteHeader();
428            JAXBContext jaxb = JAXBContext.newInstance(org.kuali.rice.kew.api.document.Document.class);
429            Marshaller marshaller = jaxb.createMarshaller();
430            marshaller.marshal(document.getDocument(), emailNodeElem);
431            emailNodeElem.appendChild(doc.importNode(dom.getDocumentElement(), true));
432            Element dConElem = XmlHelper.readXml(document.getDocumentContent().getApplicationContent())
433                    .getDocumentElement(); //Add document Content element for
434            emailNodeElem.appendChild(doc.importNode(dConElem, true)); //access by the stylesheet when creating the email
435            return doc;
436        }
437    
438        protected DocumentBuilder getDocumentBuilder(boolean coalesce) throws Exception {
439            DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
440            dbf.setCoalescing(coalesce);
441            return dbf.newDocumentBuilder();
442        }
443    
444        /* Upgrade Changes 0914 to 1011 */
445        /*
446        protected boolean isProduction() {
447        return EdenConstants.PROD_DEPLOYMENT_CODE.equalsIgnoreCase(Core.getCurrentContextConfig().getEnvironment());
448        }
449        */
450        protected boolean isProduction() {
451            return ConfigContext.getCurrentContextConfig().isProductionEnvironment();
452        }
453    
454        protected boolean isEmailListValid(List<String> emailList) {
455            Pattern p = Pattern.compile("^\\.|^\\@");
456            Matcher m = null;
457            for (String emailAddress : emailList) {
458                m = p.matcher(emailAddress);
459                if (m.find()) {
460                    //System.err.println("Email addresses don't start with dots or @ signs.");
461                    return false;
462                }
463            }
464            p = Pattern.compile("^www\\.");
465            for (String emailAddress : emailList) {
466                m = p.matcher(emailAddress);
467                if (m.find()) {
468                    //System.err.println("Email addresses don't start with \"www.\", only web pages do.");
469                    return false;
470                }
471            }
472            // find illegal characters.
473            p = Pattern.compile("[^A-Za-z0-9\\.\\@_\\-~#]+");
474            for (String emailAddress : emailList) {
475                // strip comma at end if there is one.
476                String e2 = stripComma(emailAddress);
477                m = p.matcher(e2);
478                if (m.find()) {
479                    //System.err.println("Email address contains illegal character(s).");
480                    return false;
481                }
482            }
483            // email address should match this pattern.
484            p = Pattern.compile("^([a-zA-Z0-9_\\-\\.]+)\\@([a-zA-Z0-9_\\-\\.]+)\\.([a-zA-Z]{2,5})$");
485            for (String emailAddress : emailList) {
486                String e2 = stripComma(emailAddress);
487                m = p.matcher(e2);
488                if (!m.find()) {
489                    //System.err.println("Illegal Email address format.");
490                    return false;
491                }
492            }
493            return true;
494        }
495    
496        protected String stripComma(String s) {
497            String sNew = "";
498            if (s.endsWith(",")) {
499                int x = s.length() - 1;
500                sNew = s.substring(0, x);
501            } else {
502                sNew = s;
503            }
504            return sNew;
505        }
506    
507        protected List<String> stringToList(String to) {
508            List<String> recipientAddresses = new ArrayList<String>();
509            StringTokenizer st = new StringTokenizer(to, " ", false);
510            while (st.hasMoreTokens()) {
511                recipientAddresses.add(st.nextToken());
512            }
513            return recipientAddresses;
514        }
515    
516        protected Templates loadStyleSheet(String styleName) {
517            try {
518                Templates style = CoreServiceApiServiceLocator.getStyleService().getStyleAsTranslet(styleName);
519                if (style == null) {
520                    throw new WorkflowRuntimeException("Failed to locate stylesheet with name '" + styleName + "'");
521                }
522                return style;
523            } catch (TransformerConfigurationException tce) {
524                throw new WorkflowRuntimeException("Failed to load stylesheet with name '" + styleName + "'");
525            }
526        }
527    
528        public static void addNotes(Document doc, NoteForm form) {
529            Element noteForm = EDLXmlUtils.getOrCreateChildElement(doc.getDocumentElement(), "NoteForm", true);
530            if (form.getShowEdit() != null) {
531                Element showEdit = EDLXmlUtils.getOrCreateChildElement(noteForm, "showEdit", true);
532                showEdit.appendChild(doc.createTextNode(form.getShowEdit().toLowerCase()));
533            } else {
534                Element showEdit = EDLXmlUtils.getOrCreateChildElement(noteForm, "showEdit", true);
535                showEdit.appendChild(doc.createTextNode("no"));
536            }
537            if (form.getShowAdd() != null) {
538                Element showAdd = EDLXmlUtils.getOrCreateChildElement(noteForm, "showAdd", true);
539                showAdd.appendChild(doc.createTextNode(form.getShowAdd().toString().toLowerCase()));
540            }
541            if (form.getCurrentUserName() != null) {
542                Element currentUserName = EDLXmlUtils.getOrCreateChildElement(noteForm, "currentUserName", true);
543                currentUserName.appendChild(doc.createTextNode(form.getCurrentUserName()));
544            }
545            if (form.getCurrentDate() != null) {
546                Element currentDate = EDLXmlUtils.getOrCreateChildElement(noteForm, "currentDate", true);
547                currentDate.appendChild(doc.createTextNode(form.getCurrentDate()));
548            }
549            if (form.getNoteIdNumber() != null) {
550                Element noteIdNumber = EDLXmlUtils.getOrCreateChildElement(noteForm, "noteIdNumber", true);
551                noteIdNumber.appendChild(doc.createTextNode(form.getNoteIdNumber().toString()));
552            }
553            if (form.getDocId() != null) {
554                Element docId = EDLXmlUtils.getOrCreateChildElement(noteForm, "docId", true);
555                docId.appendChild(doc.createTextNode((form.getDocId().toString())));
556            }
557            if (form.getSortNotes() != null) {
558                Element sortNotes = EDLXmlUtils.getOrCreateChildElement(noteForm, "sortNotes", true);
559                sortNotes.appendChild(doc.createTextNode(form.getSortNotes().toString().toLowerCase()));
560            }
561            if (form.getSortOrder() != null) {
562                Element sortOrder = EDLXmlUtils.getOrCreateChildElement(noteForm, "sortOrder", true);
563                sortOrder.appendChild(doc.createTextNode(form.getSortOrder().toUpperCase()));
564            }
565            if (form.getNumberOfNotes() != null) {
566                Element numberOfNotes = EDLXmlUtils.getOrCreateChildElement(noteForm, "numberOfNotes", true);
567                numberOfNotes.appendChild(doc.createTextNode(form.getNumberOfNotes().toString()));
568            }
569            if (form.getAuthorizedToAdd() != null) {
570                Element authorizedToAdd = EDLXmlUtils.getOrCreateChildElement(noteForm, "authorizedToAdd", true);
571                authorizedToAdd.appendChild(doc.createTextNode(form.getAuthorizedToAdd().toString().toLowerCase()));
572            }
573            if (form.getNumberOfNotes().intValue() > 0) {
574                Element notes = EDLXmlUtils.getOrCreateChildElement(noteForm, "Notes", true);
575                for (Iterator i = form.getNoteList().iterator(); i.hasNext();) {
576                    Note noteObj = (Note) i.next();
577                    Element note = notes.getOwnerDocument().createElement("Note");
578                    notes.appendChild(note);
579                    // Element note = Util.getOrCreateChildElement(notes, "Note",
580                    // true);
581                    if (noteObj.getNoteId() != null) {
582                        Element noteId = EDLXmlUtils.getOrCreateChildElement(note, "noteId", true);
583                        noteId.appendChild(doc.createTextNode(noteObj.getNoteId().toString()));
584                    }
585                    if (noteObj.getFormattedCreateDate() != null) {
586                        Element formattedCreateDate = EDLXmlUtils
587                                .getOrCreateChildElement(note, "formattedCreateDate", true);
588                        formattedCreateDate.appendChild(doc.createTextNode(noteObj.getFormattedCreateDate()));
589                    }
590                    if (noteObj.getFormattedCreateTime() != null) {
591                        Element formattedCreateTime = EDLXmlUtils
592                                .getOrCreateChildElement(note, "formattedCreateTime", true);
593                        formattedCreateTime.appendChild(doc.createTextNode(noteObj.getFormattedCreateTime()));
594                    }
595                    if (noteObj.getNoteAuthorFullName() != null) {
596                        Element noteAuthorFullName = EDLXmlUtils.getOrCreateChildElement(note, "noteAuthorFullName", true);
597                        noteAuthorFullName.appendChild(doc.createTextNode(noteObj.getNoteAuthorFullName()));
598                    }
599                    if (noteObj.getNoteText() != null) {
600                        Element noteText = EDLXmlUtils.getOrCreateChildElement(note, "noteText", true);
601                        noteText.appendChild(doc.createTextNode(noteObj.getNoteText()));
602                    }
603                    if (noteObj.getEditingNote() != null) {
604                        Element editingNote = EDLXmlUtils.getOrCreateChildElement(note, "editingNote", true);
605                        editingNote.appendChild(doc.createTextNode(noteObj.getEditingNote().toString()));
606                    }
607                    if (noteObj.getAuthorizedToEdit() != null) {
608                        Element authorizedToEdit = EDLXmlUtils.getOrCreateChildElement(note, "authorizedToEdit", true);
609                        authorizedToEdit.appendChild(doc.createTextNode(noteObj.getAuthorizedToEdit().toString()));
610                    }
611                    if (!noteObj.getAttachments().isEmpty()) {
612                        Element attachments = EDLXmlUtils.getOrCreateChildElement(note, "attachments", true);
613                        for (Iterator j = noteObj.getAttachments().iterator(); j.hasNext();) {
614                            Attachment attachmentObj = (Attachment) j.next();
615                            Element attachment = EDLXmlUtils.getOrCreateChildElement(attachments, "attachment", true);
616                            Element attachmentId = EDLXmlUtils.getOrCreateChildElement(attachment, "attachmentId", true);
617                            attachmentId.appendChild(doc.createTextNode(attachmentObj.getAttachmentId().toString()));
618                            Element fileName = EDLXmlUtils.getOrCreateChildElement(attachment, "fileName", true);
619                            fileName.appendChild(doc.createTextNode(attachmentObj.getFileName()));
620                        }
621                    }
622                }
623            }
624    
625        }
626    
627        private static class NoteForm {
628            private String showEdit;
629            private Boolean showAdd;
630            private String noteIdNumber;
631            private Integer numberOfNotes = new Integer(0);
632            private String sortOrder = "DESCENDING";
633            private Boolean sortNotes;
634            private String currentUserName;
635            private String currentDate;
636            private Boolean authorizedToAdd;
637            private List noteList;
638            private String addText;
639            private Long idInEdit;
640            private Note note;
641            private String noteText;
642            private String docId;
643            private String methodToCall;
644            private FileItem file;
645    
646            public NoteForm(RequestParser requestParser) {
647    
648                showEdit = requestParser.getParameterValue("showEdit");
649                if (!org.apache.commons.lang.StringUtils.isEmpty(requestParser.getParameterValue("showAdd"))) {
650                    showAdd = Boolean.valueOf(requestParser.getParameterValue("showAdd"));
651                }
652                if (!org.apache.commons.lang.StringUtils.isEmpty(requestParser.getParameterValue("noteIdNumber"))) {
653                    noteIdNumber = requestParser.getParameterValue("noteIdNumber");
654                }
655                methodToCall = requestParser.getParameterValue("methodToCall");
656                sortOrder = "DESCENDING";
657                if (!org.apache.commons.lang.StringUtils.isEmpty(requestParser.getParameterValue("sortNotes"))) {
658                    sortNotes = Boolean.valueOf(requestParser.getParameterValue("sortNotes"));
659                }
660                addText = requestParser.getParameterValue("addText");
661                noteText = requestParser.getParameterValue("noteText");
662                if (!org.apache.commons.lang.StringUtils.isEmpty(requestParser.getParameterValue("idInEdit"))) {
663                    idInEdit = Long.valueOf(requestParser.getParameterValue("idInEdit"));
664                }
665                if (noteIdNumber != null) {
666                    note = KEWServiceLocator.getNoteService().getNoteByNoteId(noteIdNumber);
667                }
668                if (requestParser.getUploadList() != null && !requestParser.getUploadList().isEmpty()) {
669                    file = (FileItem) requestParser.getUploadList().get(0);
670                }
671            }
672    
673            public String getAddText() {
674                return addText;
675            }
676    
677            public void setAddText(String addText) {
678                this.addText = addText;
679            }
680    
681            public Boolean getAuthorizedToAdd() {
682                return authorizedToAdd;
683            }
684    
685            public void setAuthorizedToAdd(Boolean authorizedToAdd) {
686                this.authorizedToAdd = authorizedToAdd;
687            }
688    
689            public String getCurrentDate() {
690                return currentDate;
691            }
692    
693            public void setCurrentDate(String currentDate) {
694                this.currentDate = currentDate;
695            }
696    
697            public String getCurrentUserName() {
698                return currentUserName;
699            }
700    
701            public void setCurrentUserName(String currentUserName) {
702                this.currentUserName = currentUserName;
703            }
704    
705            public Long getIdInEdit() {
706                return idInEdit;
707            }
708    
709            public void setIdInEdit(Long idInEdit) {
710                this.idInEdit = idInEdit;
711            }
712    
713            public Note getNote() {
714                return note;
715            }
716    
717            public void setNote(Note note) {
718                this.note = note;
719            }
720    
721            public String getNoteIdNumber() {
722                return noteIdNumber;
723            }
724    
725            public void setNoteIdNumber(String noteIdNumber) {
726                this.noteIdNumber = noteIdNumber;
727            }
728    
729            public List getNoteList() {
730                return noteList;
731            }
732    
733            public void setNoteList(List noteList) {
734                this.noteList = noteList;
735            }
736    
737            public String getNoteText() {
738                return noteText;
739            }
740    
741            public void setNoteText(String noteText) {
742                this.noteText = noteText;
743            }
744    
745            public Integer getNumberOfNotes() {
746                return numberOfNotes;
747            }
748    
749            public void setNumberOfNotes(Integer numberOfNotes) {
750                this.numberOfNotes = numberOfNotes;
751            }
752    
753            public Boolean getShowAdd() {
754                return showAdd;
755            }
756    
757            public void setShowAdd(Boolean showAdd) {
758                this.showAdd = showAdd;
759            }
760    
761            public String getShowEdit() {
762                return showEdit;
763            }
764    
765            public void setShowEdit(String showEdit) {
766                this.showEdit = showEdit;
767            }
768    
769            public Boolean getSortNotes() {
770                return sortNotes;
771            }
772    
773            public void setSortNotes(Boolean sortNotes) {
774                this.sortNotes = sortNotes;
775            }
776    
777            public String getSortOrder() {
778                return sortOrder;
779            }
780    
781            public void setSortOrder(String sortOrder) {
782                this.sortOrder = sortOrder;
783            }
784    
785            public String getDocId() {
786                return docId;
787            }
788    
789            public void setDocId(String docId) {
790                this.docId = docId;
791            }
792    
793            public String getMethodToCall() {
794                return methodToCall;
795            }
796    
797            public void setMethodToCall(String methodToCall) {
798                this.methodToCall = methodToCall;
799            }
800    
801            public FileItem getFile() {
802                return file;
803            }
804    
805            public void setFile(FileItem file) {
806                this.file = file;
807            }
808        }
809    
810        /**
811         * Method added for notes editing function. Called by retrieveNoteList method
812         * @param allNotes
813         * @param sortOrder
814         * @return
815         */
816    
817        private List sortNotes(List allNotes, String sortOrder) {
818            final int returnCode = KewApiConstants.Sorting.SORT_SEQUENCE_DSC.equalsIgnoreCase(sortOrder) ? -1 : 1;
819    
820            try {
821                Collections.sort(allNotes,
822                        new Comparator() {
823                            public int compare(Object o1, Object o2) {
824                                Timestamp date1 = ((Note) o1).getNoteCreateDate();
825                                Timestamp date2 = ((Note) o2).getNoteCreateDate();
826    
827                                if (date1.before(date2)) {
828                                    return returnCode * -1;
829                                } else if (date1.after(date2)) {
830                                    return returnCode;
831                                } else {
832                                    return 0;
833                                }
834                            }
835                        });
836            } catch (Throwable e) {
837                LOG.error(e.getMessage(), e);
838            }
839            return allNotes;
840        }
841    
842        /**
843         * Method added for notes editing function. Called by retrieveNoteList method
844         * @param note
845         * @throws Exception
846         */
847    
848        private void getAuthorData(Note note) throws Exception {
849            Person workflowUser = null;
850            String id = "";
851            if (note != null && note.getNoteAuthorWorkflowId() != null
852                    && !"".equalsIgnoreCase(note.getNoteAuthorWorkflowId())) {
853                workflowUser = KimApiServiceLocator.getPersonService().getPerson(note.getNoteAuthorWorkflowId());
854                id = note.getNoteAuthorWorkflowId();
855            }
856            if (workflowUser != null) {
857                note.setNoteAuthorFullName(workflowUser.getName());
858                note.setNoteAuthorEmailAddress(workflowUser.getEmailAddress());
859                note.setNoteAuthorNetworkId(workflowUser.getPrincipalName());
860            } else {
861                note.setNoteAuthorFullName(id + " (Name not Available)");
862                note.setNoteAuthorEmailAddress("Not Available");
863                note.setNoteAuthorNetworkId("Not Available");
864            }
865        }
866    
867        public String getCurrentDate() {
868            Date currentDate = new Date();
869            DateFormat dateFormat = RiceConstants.getDefaultDateFormat();
870            return dateFormat.format(currentDate);
871        }
872    
873        /**
874         * Method added for notes editing function.
875         * @return
876         */
877        private NoteService getNoteService() {
878            return (NoteService) KEWServiceLocator.getService(KEWServiceLocator.NOTE_SERVICE);
879        }
880    
881        /**
882         * Method added for notes editing function.
883         * @return
884         */
885        private RouteHeaderService getRouteHeaderService() {
886            return (RouteHeaderService) KEWServiceLocator.getService(KEWServiceLocator.DOC_ROUTE_HEADER_SRV);
887        }
888    }