alvinalexander.com | career | drupal | java | mac | mysql | perl | scala | uml | unix  

What this is

This file is included in the DevDaily.com "Java Source Code Warehouse" project. The intent of this project is to help you "Learn Java by Example" TM.

Other links

The source code

/*
 *                 Sun Public License Notice
 *
 * The contents of this file are subject to the Sun Public License
 * Version 1.0 (the "License"). You may not use this file except in
 * compliance with the License. A copy of the License is available at
 * http://www.sun.com/
 *
 * The Original Code is Forte for Java, Community Edition. The Initial
 * Developer of the Original Code is Sun Microsystems, Inc. Portions
 * Copyright 1997-2001 Sun Microsystems, Inc. All Rights Reserved.
 */

package org.netbeans.modules.web.xmlutils;

import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import org.w3c.dom.Node;
import org.w3c.dom.CharacterData;
import java.util.*;

import org.openide.NotifyDescriptor;
import org.openide.util.NbBundle;
import java.text.MessageFormat;
import org.openide.DialogDisplayer;

import org.xml.sax.*;

/** Static methods useful for XMLJ2eeDataObject.
 *
 * @author  mkuchtiak
 */

public class XMLJ2eeUtils {
    
    /** This method updates document in editor with newDoc, but leaves the text before prefixMark.
     * @param doc original document
     * @param newDoc new value of whole document
     * @param prefixMark - beginning part of the document before this mark should be preserved
     */
    public static void updateDocument(javax.swing.text.Document doc, String newDoc, String prefixMark) throws javax.swing.text.BadLocationException {
        int origLen = doc.getLength();        
        String origDoc = doc.getText(0, origLen);;
        int prefixInd=0;
        if (prefixMark!=null) {
            prefixInd = origDoc.indexOf(prefixMark);
            if (prefixInd>0) {
                origLen-=prefixInd;
                origDoc=doc.getText(prefixInd,origLen);
            }
            else {
                prefixInd=0;
            }
            int prefixIndNewDoc=newDoc.indexOf(prefixMark);
            if (prefixIndNewDoc>0)
            newDoc=newDoc.substring(prefixIndNewDoc);
        }
        //newDoc=filterEndLines(newDoc);
        int newLen = newDoc.length();
        
        if (origDoc.equals(newDoc)) {
            // no change in document
            return;
        }

        final int granularity = 20;
        
        int prefix = -1;
        int postfix = -1;
        String toInsert = newDoc;
        
        if ((origLen > granularity) && (newLen > granularity)) {
            int pos1 = 0;
            int len = Math.min(origLen, newLen);
            // find the prefix which both Strings begin with
            for (;;) {
                if (origDoc.regionMatches(pos1, newDoc, pos1, granularity)) {
                    pos1 += granularity;
                    if (pos1 + granularity >= len) {
                        break;
                    }
                }
                else {
                    break;
                }
            }
            if (pos1 > 0)
                prefix = pos1;
            
            pos1 = origLen - granularity;
            int pos2 = newLen - granularity;
            for (;;) {
                if (origDoc.regionMatches(pos1, newDoc, pos2, granularity)) {
                    pos1 -= granularity;
                    pos2 -= granularity;
                    if (pos1 < 0) {
                        pos1 += granularity;
                        break;
                    }
                    if (pos2 < 0) {
                        pos2 += granularity;
                        break;
                    }
                }
                else {
                    pos1 += granularity;
                    pos2 += granularity;
                    break;
                }
            }
            if (pos1 < origLen - granularity) {
                postfix = pos1;
            }
        }

        if ((prefix != -1) && (postfix != -1)) {
            if (postfix < prefix) {
                postfix = prefix;
            }
            
            int delta = (prefix + (origLen - postfix) - newLen);
            if (delta > 0) {
                postfix += delta;
            }
        }
        
        int removeBeginIndex = (prefix == -1) ? 0 : prefix;
        int removeEndIndex = (postfix == -1) ? origLen - 1 : postfix;
        
        doc.remove(prefixInd+removeBeginIndex, removeEndIndex - removeBeginIndex);

        if (toInsert.length() > 0) {
            int p1 = (prefix == -1) ? 0 : prefix;
            int p2 = toInsert.length();
            if (postfix != -1)
                p2 = p2 - (origLen - postfix);

            if (p2 > p1) {
                toInsert = toInsert.substring(p1, p2);
                doc.insertString(prefixInd+removeBeginIndex, toInsert, null);
            }
        }        
    }
    /** This method update document in editor after change in beans hierarchy.
     * It takes old document and new document in String.
     * To avoid regeneration of whole document in text editor following steps are done:
     *  1) compare the begin of both documents (old one and new one)
     *     - find the first position where both documents differ
     *  2) do the same from the ends of documents
     *  3) remove old middle part of text (modified part) and insert new one
     * 
     * @param doc original document
     * @param newDoc new value of whole document
     * @param prefixMark - beginning part of the document before this mark should be preserved
     */
    public static void replaceDocument(javax.swing.text.Document doc, String newDoc, String prefixMark) throws javax.swing.text.BadLocationException {
        int origLen = doc.getLength();        
        String origDoc = doc.getText(0, origLen);
        int prefixInd=0;
        if (prefixMark!=null) {
            prefixInd = origDoc.indexOf(prefixMark);
            if (prefixInd>0) {
                origLen-=prefixInd;
                origDoc=doc.getText(prefixInd,origLen);
            }
            else {
                prefixInd=0;
            }
            int prefixIndNewDoc=newDoc.indexOf(prefixMark);
            if (prefixIndNewDoc>0)
            newDoc=newDoc.substring(prefixIndNewDoc);
        }
        newDoc=filterEndLines(newDoc);
        int newLen = newDoc.length();
        
        if (origDoc.equals(newDoc)) {
            // no change in document
            return;
        }

        final int granularity = 20;
        
        int prefix = -1;
        int postfix = -1;
        String toInsert = newDoc;
        
        if ((origLen > granularity) && (newLen > granularity)) {
            int pos1 = 0;
            int len = Math.min(origLen, newLen);
            // find the prefix which both Strings begin with
            for (;;) {
                if (origDoc.regionMatches(pos1, newDoc, pos1, granularity)) {
                    pos1 += granularity;
                    if (pos1 + granularity >= len) {
                        break;
                    }
                }
                else {
                    break;
                }
            }
            if (pos1 > 0)
                prefix = pos1;
            
            pos1 = origLen - granularity;
            int pos2 = newLen - granularity;
            for (;;) {
                if (origDoc.regionMatches(pos1, newDoc, pos2, granularity)) {
                    pos1 -= granularity;
                    pos2 -= granularity;
                    if (pos1 < 0) {
                        pos1 += granularity;
                        break;
                    }
                    if (pos2 < 0) {
                        pos2 += granularity;
                        break;
                    }
                }
                else {
                    pos1 += granularity;
                    pos2 += granularity;
                    break;
                }
            }
            if (pos1 < origLen - granularity) {
                postfix = pos1;
            }
        }

        if ((prefix != -1) && (postfix != -1)) {
            if (postfix < prefix) {
                postfix = prefix;
            }
            
            int delta = (prefix + (origLen - postfix) - newLen);
            if (delta > 0) {
                postfix += delta;
            }
        }
        
        int removeBeginIndex = (prefix == -1) ? 0 : prefix;
        int removeEndIndex;
        if (postfix == -1){
            if(doc.getText(0, doc.getLength()).charAt(doc.getLength()-1) == '>'){
                removeEndIndex = origLen;
            }
            else
                removeEndIndex = origLen-1;
        }
        else 
            removeEndIndex = postfix;
        
        doc.remove(prefixInd+removeBeginIndex, removeEndIndex - removeBeginIndex);
        
        if (toInsert.length() > 0) {
            int p1 = (prefix == -1) ? 0 : prefix;
            int p2 = toInsert.length();
            if (postfix != -1)
                p2 = p2 - (origLen - postfix);

            if (p2 > p1) {
                toInsert = toInsert.substring(p1, p2);
                doc.insertString(prefixInd+removeBeginIndex, toInsert, null);
            }
        }
    }
    
    public static void replaceDocument(javax.swing.text.Document doc, String newDoc) throws javax.swing.text.BadLocationException {
        replaceDocument(doc,newDoc,null);
    }
    /** Filter characters #13 (CR) from the specified String
     * @param str original string
     * @return the string without #13 characters
     */
    public static String filterEndLines(String str) {
        char[] text = str.toCharArray();
        int pos = 0;
        for (int i = 0; i < text.length; i++) {
            char c = text[i];
            if (c != 13) {
                if (pos != i)
                    text[pos] = c;
                pos++;
            }
        }
        return new String(text, 0, pos - 1);
    }
    /** This method updates the attribute specified by the elementPath in DOM tree
     * @param root Root element of the DOM graph 
     * @param elementPath List defining the element path to the target element 
     * @param attrName Attribute name of the target attribute 
     * @param attrValue New value for the attribute defined by attrName
     * @return true if method was succesful, false otherwise
     */    
    public static boolean changeAttribute (Element root, List elementPath, String attrName, String attrValue)
    throws org.w3c.dom.DOMException {
       
        //if (elementPath.size()==0) return false;
        if (elementPath==null) return false;
        Iterator it = elementPath.iterator();
        Element element = root;
        String keyAttributeName=null;
        NodeList lastNodeList=null;
        int elementIndex=-1; 
        while (it.hasNext()){
            elementIndex=-1;
            ElementAttrInfo info = (ElementAttrInfo)it.next();
            String attributeName = info.getAttributeName();
            String attributeValue = info.getAttributeValue();
            NodeList nodeList = element.getElementsByTagName(info.getElementName());
            if (nodeList.getLength()==0) return false;
            lastNodeList = nodeList;
            Element newElement=null;
            if (attributeName==null) { // there is only one element
                newElement = (Element)nodeList.item(0);
            } else { // element need to be found by element value
                for (int i=0;i=0 && attrName.equals(keyAttributeName)) {
                for (int i=0;i=0;i--){
            Node item = list.item(i);
            Node previous = item.getPreviousSibling();
            if (previous!=null && previous instanceof CharacterData)
                element.removeChild(previous);
            element.removeChild(item);
        }
        
        return true;
    }
    
    private static void showDialog(String elementName, String attrName, String attrValue){
     String mes = MessageFormat.format (NbBundle.getMessage(XMLJ2eeUtils.class, "TXT_elementExists"),
     new Object [] {elementName,attrName,attrValue});
     NotifyDescriptor.Message message = new NotifyDescriptor.Message(mes);
     DialogDisplayer.getDefault().notify(message);
    }
    
    private static String getIndentBefore(int level) {
        StringBuffer sb = new StringBuffer("\n"); //NOI18N
        for (int i=0;i<=level;i++) sb.append("  "); //NOI18N
        return sb.toString();
    }
    private static String getIndentAfter(int level) {
        StringBuffer sb = new StringBuffer("\n"); //NOI18N
        for (int i=0;i values inside the  elements (in web.xml)
    */    
    public static Set getTagValues (java.io.InputStream is, String elName, String tagName) throws java.io.IOException, SAXException {
        return getTagValues(is,new String[]{elName},tagName);
    }
    /** Parsing to get Set of Strings that correpond to tagName valeus inside elNames, e.g.:
     *  to get all  values inside the  and  elements (in TLD)
    */
    public static Set getTagValues (java.io.InputStream is, String[] elNames, String tagName) throws java.io.IOException, SAXException {
        javax.xml.parsers.SAXParserFactory fact = javax.xml.parsers.SAXParserFactory.newInstance();
        fact.setValidating(false);
        try {
            javax.xml.parsers.SAXParser parser = fact.newSAXParser();
            XMLReader reader = parser.getXMLReader();
            VersionHandler handler = new VersionHandler(elNames,tagName);
            reader.setContentHandler(handler);
            try {
                reader.parse(new InputSource(is));
            } catch (SAXException ex) {
                String message = ex.getMessage();
            }
            return handler.getValues();
        } catch(javax.xml.parsers.ParserConfigurationException ex) {
            return new java.util.HashSet();
        }
    }
    
    private static class VersionHandler extends org.xml.sax.helpers.DefaultHandler {
        private String tagName;
        private Set elNames;
        private Set values;
        private boolean insideEl, insideTag;

        VersionHandler(String[] elNames, String tagName) {
            this.elNames=new java.util.HashSet();
            for (int i=0;i
... this post is sponsored by my books ...

#1 New Release!

FP Best Seller

 

new blog posts

 

Copyright 1998-2021 Alvin Alexander, alvinalexander.com
All Rights Reserved.

A percentage of advertising revenue from
pages under the /java/jwarehouse URI on this website is
paid back to open source projects.