<commit_before>//
// This file is part of the OpenNMS(R) Application.
//
// OpenNMS(R) is Copyright (C) 2002-2003 The OpenNMS Group, Inc.  All rights reserved.
// OpenNMS(R) is a derivative work, containing both original code, included code and modified
// code that was published under the GNU General Public License. Copyrights for modified 
// and included code are below.
//
// OpenNMS(R) is a registered trademark of The OpenNMS Group, Inc.
//
// Copyright (C) 1999-2001 Oculan Corp.  All rights reserved.
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
//
// For more information contact:
//      OpenNMS Licensing       <<EMAIL>>
//      http://www.opennms.org/
//      http://www.opennms.com/
//
// Tab Size = 8
//

package org.opennms.web;

import java.io.UnsupportedEncodingException;
import java.lang.reflect.UndeclaredThrowableException;
import java.net.InetAddress;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.net.UnknownHostException;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;

import javax.servlet.http.HttpServletRequest;

import org.opennms.core.resource.Vault;
import org.opennms.netmgt.utils.EventProxy;
import org.opennms.netmgt.utils.TcpEventProxy;
import org.opennms.web.element.NetworkElementFactory;

/**
 * Provides convenience functions for web-based interfaces.
 * 
 * @author <A HREF="mailto:<EMAIL>"><NAME> </A>
 * @author <A HREF="http://www.opennms.org/">OpenNMS </A>
 */
public abstract class Util extends Object {

    /**
     * Internal flag used to cache a servlet context parameter
     */
    protected static Boolean usePortInBaseUrls;

    /**
     * Return a string that represents the fully qualified URL for our servlet
     * context, suitable for use in the HTML <em>base</em> tag.
     * 
     * <p>
     * As an example, suppose your host was www.mycompany.com, you are serving
     * from port 80, and your web application name was "opennms," then this
     * method would return: <code>http://www.mycompany.com:80/opennms/</code>
     * </p>
     * 
     * @param request
     *            the servlet request you are servicing
     */
    public static String calculateUrlBase(HttpServletRequest request) {
        if (request == null) {
            throw new IllegalArgumentException("Cannot take null parameters.");
        }

        // get what the web browser thinks is the URL
        StringBuffer buffer = request.getRequestURL();

        // get a string version of the buffer so we can search in it
        String string = buffer.toString();

        // find the "//" in something like "http://host"
        int schemeSlashesIndex = string.indexOf("//");

        // find the "/" at the end of "http://host:port/"
        int schemeHostPortIndex = string.indexOf("/", schemeSlashesIndex + 2);

        // truncate everything after the base scheme, host, and port values
        buffer.setLength(schemeHostPortIndex);

        String context = request.getContextPath();

        // if the context is not the root context
        if (!context.equals("")) {
            // context will always start with a slash
            buffer.append(context);
        }

        // add a trailing slash
        buffer.append("/");

        return buffer.toString();
    }

    /**
     * Convenience method for resolving the human-readable hostname for an IP
     * address, if at all possible. If the hostname cannot be found, this method
     * returns the IP address parameter.
     * 
     * @param ipAddress
     *            the IP address for which you want the hostname
     * @deprecated Please use {@link NetworkElementFactory#getHostname
     *             NetworkElementFactory.getHostname} instead.
     */
    public static String getHostname(String ipAddress) {
        String hostname = ipAddress;

        try {
            hostname = NetworkElementFactory.getHostname(ipAddress);
        } catch (Exception e) {
            // ignore this exception and just return the IP address
        }

        return (hostname);
    }

    /**
     * Encapsulate the deprecated encode method to fix it in one place.
     * 
     * @param string
     *            string to be encoded
     * @return encoded string
     */
    public static String encode(String string) {
        try {
            return URLEncoder.encode(string, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            // UTF-8 should *never* throw this
            throw new UndeclaredThrowableException(e);
        }
    }

    /**
     * Encapsulate the deprecated decode method to fix it in one place.
     * 
     * @param string
     *            string to be decoded
     * @return decoded string
     */
    public static String decode(String string) {
        try {
            return URLDecoder.decode(string, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            // UTF-8 should *never* throw this
            throw new UndeclaredThrowableException(e);
        }
    }

    /**
     * Convenience method for resolving the human-readable hostname for an IP
     * address, if at all possible. If the hostname cannot be found, from the
     * table, this method returns the IP address parameter. This method doesnt
     * throw any exception.
     * 
     * @param ipAddress
     *            the IP address for which you want the hostname
     * @deprecated Please use {@link NetworkElementFactory#getHostname
     *             NetworkElementFactory.getHostname} instead.
     */
    public static String resolveIpAddress(String ipAddress) {
        String hostname = ipAddress;

        try {
            hostname = NetworkElementFactory.getHostname(ipAddress);
        } catch (Exception e) {
            // ignore this exception and just return the IP address
        }

        return (hostname);
    }

    /**
     * Method used to convert an integer bits-per-second value and a more
     * commonly recognized abbreviation for network interface speeds. Feel free
     * to expand it as necessary to accomodate different values.
     * 
     * @param ifSpeed
     *            The bits-per-second value to be converted into a string
     *            description
     * @return A string representation of the speed (&quot;100 Mbps&quot; for
     *         example)
     */
    public static String getHumanReadableIfSpeed(long ifSpeed) {
        if (ifSpeed == 10000000L)
            return "10 Mbps";
        else if (ifSpeed == 100000000L)
            return "100 Mbps";
        else if (ifSpeed == 1000000000L)
            return "1.0 Gbps";
        else if (ifSpeed == 10000000000L)
            return "10.0 Gbps";
        else
            return (String.valueOf(ifSpeed) + " bps");
    }

    /**
     * Creates hidden tags for all the parameters given in the request.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter.
     */
    public static String makeHiddenTags(HttpServletRequest request) {
        return (makeHiddenTags(request, new HashMap(), new String[0]));
    }

    /**
     * Creates hidden tags for all the parameters given in the request.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a map of extra parameters to create hidden tags for
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter.
     */
    public static String makeHiddenTags(HttpServletRequest request, Map additions) {
        return (makeHiddenTags(request, additions, new String[0]));
    }

    /**
     * Creates hidden tags for all the parameters given in the request.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param ignores
     *            A string array containing request parameters to ignore
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter.
     */
    public static String makeHiddenTags(HttpServletRequest request, String[] ignores) {
        return (makeHiddenTags(request, new HashMap(), ignores));
    }

    /**
     * Creates hidden tags for all the parameters given in the request plus the
     * additions, except for the parameters and additions listed in the ignore
     * list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a map of extra parameters to create hidden tags for
     * @param ignores
     *            the list of parameters not to create a hidden tag for
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter not in the ignore list.
     */
    public static String makeHiddenTags(HttpServletRequest request, Map additions, String[] ignores) {
        return (makeHiddenTags(request, additions, ignores, IgnoreType.BOTH));
    }

    /**
     * Creates hidden tags for all the parameters given in the request plus the
     * additions, except for the parmeters listed in the ignore list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a map of extra parameters to create hidden tags for
     * @param ignores
     *            the list of parameters not to create a hidden tag for
     * @param ignoreType
     *            whether the ignore list applies to the request parameters,
     *            values in the additions map, or both
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter not in the ignore list.
     */
    public static String makeHiddenTags(HttpServletRequest request, Map additions, String[] ignores, IgnoreType ignoreType) {
        if (request == null || additions == null || ignores == null || ignoreType == null) {
            throw new IllegalArgumentException("Cannot take null parameters.");
        }

        StringBuffer buffer = new StringBuffer();

        ArrayList ignoreList = new ArrayList();
        for (int i = 0; i < ignores.length; i++) {
            ignoreList.add(ignores[i]);
        }

        Enumeration names = request.getParameterNames();

        while (names.hasMoreElements()) {
            String name = (String) names.nextElement();
            String[] values = request.getParameterValues(name);

            if ((ignoreType == IgnoreType.ADDITIONS_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("<input type=\"hidden\" name=\"");
                    buffer.append(name);
                    buffer.append("\" value=\"");
                    buffer.append(values[i]);
                    buffer.append("\" />");
                    buffer.append("\n");
                }
            }
        }

        // Add the additions in
        Set keySet = additions.keySet();
        Iterator keys = keySet.iterator();

        while (keys.hasNext()) {
            String name = (String) keys.next();

            // handle both a String value or a String[] value
            Object tmp = additions.get(name);
            String[] values = (tmp instanceof String[]) ? ((String[]) tmp) : (new String[] { (String) tmp });

            if ((ignoreType == IgnoreType.REQUEST_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("<input type=\"hidden\" name=\"");
                    buffer.append(name);
                    buffer.append("\" value=\"");
                    buffer.append(values[i]);
                    buffer.append("\" />");
                    buffer.append("\n");
                }
            }
        }

        return (buffer.toString());
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code>.
     * 
     * @see #makeQueryString( HttpServletRequest, Map, String[] )
     */
    public static String makeQueryString(HttpServletRequest request) {
        return (makeQueryString(request, new HashMap(), new String[0]));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> and key in
     * given <code>Map</code>.
     * 
     * @see #makeQueryString( HttpServletRequest, Map, String[] )
     */
    public static String makeQueryString(HttpServletRequest request, Map additions) {
        return (makeQueryString(request, additions, new String[0]));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> that is not
     * listed in the ignore list.
     * 
     * @see #makeQueryString( HttpServletRequest, Map, String[] )
     */
    public static String makeQueryString(HttpServletRequest request, String[] ignores) {
        return (makeQueryString(request, new HashMap(), ignores));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> and key in
     * given <code>Map</code> that is not listed in the ignore list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a mapping of strings to strings or string arrays to be
     *            included in the query string
     * @param ignores
     *            the list of parameters and map entries not to include
     * @return A string in the <em>x-www-form-urlencoded</em> format that is
     *         suitable for adding to a URL as a query string.
     */
    public static String makeQueryString(HttpServletRequest request, Map additions, String[] ignores) {
        return (makeQueryString(request, additions, ignores, IgnoreType.BOTH));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> and key in
     * given <code>Map</code> that is not listed in the ignore list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a mapping of strings to strings or string arrays to be
     *            included in the query string
     * @param ignores
     *            the list of parameters and map entries not to include
     * @return A string in the <em>x-www-form-urlencoded</em> format that is
     *         suitable for adding to a URL as a query string.
     */
    public static String makeQueryString(HttpServletRequest request, Map additions, String[] ignores, IgnoreType ignoreType) {
        if (request == null || additions == null || ignores == null || ignoreType == null) {
            throw new IllegalArgumentException("Cannot take null parameters.");
        }

        StringBuffer buffer = new StringBuffer();

        ArrayList ignoreList = new ArrayList();
        for (int i = 0; i < ignores.length; i++) {
            ignoreList.add(ignores[i]);
        }

        Enumeration names = request.getParameterNames();

        while (names.hasMoreElements()) {
            String name = (String) names.nextElement();
            String[] values = request.getParameterValues(name);

            if ((ignoreType == IgnoreType.ADDITIONS_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("&");
                    buffer.append(name);
                    buffer.append("=");
                    buffer.append(Util.encode(values[i]));
                }
            }
        }

        Set keySet = additions.keySet();
        Iterator keys = keySet.iterator();

        while (keys.hasNext()) {
            String name = (String) keys.next();

            // handle both a String value or a String[] value
            Object tmp = additions.get(name);
            String[] values = (tmp instanceof String[]) ? ((String[]) tmp) : (new String[] { (String) tmp });

            if ((ignoreType == IgnoreType.REQUEST_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("&");
                    buffer.append(name);
                    buffer.append("=");
                    buffer.append(Util.encode(values[i]));
                }
            }
        }

        // removes the first & from the buffer
        buffer.deleteCharAt(0);

        return (buffer.toString());
    }

    public static class IgnoreType extends Object {
        public static final int _REQUEST_ONLY = 0;

        public static final int _ADDITIONS_ONLY = 0;

        public static final int _BOTH = 0;

        public static final IgnoreType REQUEST_ONLY = new IgnoreType(_REQUEST_ONLY);

        public static final IgnoreType ADDITIONS_ONLY = new IgnoreType(_ADDITIONS_ONLY);

        public static final IgnoreType BOTH = new IgnoreType(_BOTH);

        protected int value;

        private IgnoreType(int value) {
            this.value = value;
        }

        public int getValue() {
            return this.value;
        }
    }

    public static Map getOrderedMap(String names[][]) {
        TreeMap orderedMap = new TreeMap();

        for (int i = 0; i < names.length; i++) {<commit_msg>Use generics internally in functions... I was here, so I figured "sure, why not."<commit_after>//
// This file is part of the OpenNMS(R) Application.
//
// OpenNMS(R) is Copyright (C) 2002-2003 The OpenNMS Group, Inc.  All rights reserved.
// OpenNMS(R) is a derivative work, containing both original code, included code and modified
// code that was published under the GNU General Public License. Copyrights for modified 
// and included code are below.
//
// OpenNMS(R) is a registered trademark of The OpenNMS Group, Inc.
//
// Copyright (C) 1999-2001 Oculan Corp.  All rights reserved.
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
//
// For more information contact:
//      OpenNMS Licensing       <<EMAIL>>
//      http://www.opennms.org/
//      http://www.opennms.com/
//
// Tab Size = 8
//

package org.opennms.web;

import java.io.UnsupportedEncodingException;
import java.lang.reflect.UndeclaredThrowableException;
import java.net.InetAddress;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.net.UnknownHostException;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;

import javax.servlet.http.HttpServletRequest;

import org.opennms.core.resource.Vault;
import org.opennms.netmgt.utils.EventProxy;
import org.opennms.netmgt.utils.TcpEventProxy;
import org.opennms.web.element.NetworkElementFactory;

/**
 * Provides convenience functions for web-based interfaces.
 * 
 * @author <A HREF="mailto:<EMAIL>"><NAME> </A>
 * @author <A HREF="http://www.opennms.org/">OpenNMS </A>
 */
public abstract class Util extends Object {

    /**
     * Internal flag used to cache a servlet context parameter
     */
    protected static Boolean usePortInBaseUrls;

    /**
     * Return a string that represents the fully qualified URL for our servlet
     * context, suitable for use in the HTML <em>base</em> tag.
     * 
     * <p>
     * As an example, suppose your host was www.mycompany.com, you are serving
     * from port 80, and your web application name was "opennms," then this
     * method would return: <code>http://www.mycompany.com:80/opennms/</code>
     * </p>
     * 
     * @param request
     *            the servlet request you are servicing
     */
    public static String calculateUrlBase(HttpServletRequest request) {
        if (request == null) {
            throw new IllegalArgumentException("Cannot take null parameters.");
        }

        // get what the web browser thinks is the URL
        StringBuffer buffer = request.getRequestURL();

        // get a string version of the buffer so we can search in it
        String string = buffer.toString();

        // find the "//" in something like "http://host"
        int schemeSlashesIndex = string.indexOf("//");

        // find the "/" at the end of "http://host:port/"
        int schemeHostPortIndex = string.indexOf("/", schemeSlashesIndex + 2);

        // truncate everything after the base scheme, host, and port values
        buffer.setLength(schemeHostPortIndex);

        String context = request.getContextPath();

        // if the context is not the root context
        if (!context.equals("")) {
            // context will always start with a slash
            buffer.append(context);
        }

        // add a trailing slash
        buffer.append("/");

        return buffer.toString();
    }

    /**
     * Convenience method for resolving the human-readable hostname for an IP
     * address, if at all possible. If the hostname cannot be found, this method
     * returns the IP address parameter.
     * 
     * @param ipAddress
     *            the IP address for which you want the hostname
     * @deprecated Please use {@link NetworkElementFactory#getHostname
     *             NetworkElementFactory.getHostname} instead.
     */
    public static String getHostname(String ipAddress) {
        String hostname = ipAddress;

        try {
            hostname = NetworkElementFactory.getHostname(ipAddress);
        } catch (Exception e) {
            // ignore this exception and just return the IP address
        }

        return (hostname);
    }

    /**
     * Encapsulate the deprecated encode method to fix it in one place.
     * 
     * @param string
     *            string to be encoded
     * @return encoded string
     */
    public static String encode(String string) {
        try {
            return URLEncoder.encode(string, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            // UTF-8 should *never* throw this
            throw new UndeclaredThrowableException(e);
        }
    }

    /**
     * Encapsulate the deprecated decode method to fix it in one place.
     * 
     * @param string
     *            string to be decoded
     * @return decoded string
     */
    public static String decode(String string) {
        try {
            return URLDecoder.decode(string, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            // UTF-8 should *never* throw this
            throw new UndeclaredThrowableException(e);
        }
    }

    /**
     * Convenience method for resolving the human-readable hostname for an IP
     * address, if at all possible. If the hostname cannot be found, from the
     * table, this method returns the IP address parameter. This method doesnt
     * throw any exception.
     * 
     * @param ipAddress
     *            the IP address for which you want the hostname
     * @deprecated Please use {@link NetworkElementFactory#getHostname
     *             NetworkElementFactory.getHostname} instead.
     */
    public static String resolveIpAddress(String ipAddress) {
        String hostname = ipAddress;

        try {
            hostname = NetworkElementFactory.getHostname(ipAddress);
        } catch (Exception e) {
            // ignore this exception and just return the IP address
        }

        return (hostname);
    }

    /**
     * Method used to convert an integer bits-per-second value and a more
     * commonly recognized abbreviation for network interface speeds. Feel free
     * to expand it as necessary to accomodate different values.
     * 
     * @param ifSpeed
     *            The bits-per-second value to be converted into a string
     *            description
     * @return A string representation of the speed (&quot;100 Mbps&quot; for
     *         example)
     */
    public static String getHumanReadableIfSpeed(long ifSpeed) {
        if (ifSpeed == 10000000L)
            return "10 Mbps";
        else if (ifSpeed == 100000000L)
            return "100 Mbps";
        else if (ifSpeed == 1000000000L)
            return "1.0 Gbps";
        else if (ifSpeed == 10000000000L)
            return "10.0 Gbps";
        else
            return (String.valueOf(ifSpeed) + " bps");
    }

    /**
     * Creates hidden tags for all the parameters given in the request.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter.
     */
    public static String makeHiddenTags(HttpServletRequest request) {
        return (makeHiddenTags(request, new HashMap(), new String[0]));
    }

    /**
     * Creates hidden tags for all the parameters given in the request.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a map of extra parameters to create hidden tags for
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter.
     */
    public static String makeHiddenTags(HttpServletRequest request, Map additions) {
        return (makeHiddenTags(request, additions, new String[0]));
    }

    /**
     * Creates hidden tags for all the parameters given in the request.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param ignores
     *            A string array containing request parameters to ignore
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter.
     */
    public static String makeHiddenTags(HttpServletRequest request, String[] ignores) {
        return (makeHiddenTags(request, new HashMap(), ignores));
    }

    /**
     * Creates hidden tags for all the parameters given in the request plus the
     * additions, except for the parameters and additions listed in the ignore
     * list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a map of extra parameters to create hidden tags for
     * @param ignores
     *            the list of parameters not to create a hidden tag for
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter not in the ignore list.
     */
    public static String makeHiddenTags(HttpServletRequest request, Map additions, String[] ignores) {
        return (makeHiddenTags(request, additions, ignores, IgnoreType.BOTH));
    }

    /**
     * Creates hidden tags for all the parameters given in the request plus the
     * additions, except for the parmeters listed in the ignore list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a map of extra parameters to create hidden tags for
     * @param ignores
     *            the list of parameters not to create a hidden tag for
     * @param ignoreType
     *            whether the ignore list applies to the request parameters,
     *            values in the additions map, or both
     * @return A string containing an HTML &lt;input type="hidden" name="
     *         <code>paramName</code>" value=" <code>paramValue</code>"
     *         /&gt; tag for each parameter not in the ignore list.
     */
    public static String makeHiddenTags(HttpServletRequest request, Map additions, String[] ignores, IgnoreType ignoreType) {
        if (request == null || additions == null || ignores == null || ignoreType == null) {
            throw new IllegalArgumentException("Cannot take null parameters.");
        }

        StringBuffer buffer = new StringBuffer();

        ArrayList<String> ignoreList = new ArrayList<String>();
        for (int i = 0; i < ignores.length; i++) {
            ignoreList.add(ignores[i]);
        }

        Enumeration names = request.getParameterNames();

        while (names.hasMoreElements()) {
            String name = (String) names.nextElement();
            String[] values = request.getParameterValues(name);

            if ((ignoreType == IgnoreType.ADDITIONS_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("<input type=\"hidden\" name=\"");
                    buffer.append(name);
                    buffer.append("\" value=\"");
                    buffer.append(values[i]);
                    buffer.append("\" />");
                    buffer.append("\n");
                }
            }
        }

        // Add the additions in
        Set keySet = additions.keySet();
        Iterator keys = keySet.iterator();

        while (keys.hasNext()) {
            String name = (String) keys.next();

            // handle both a String value or a String[] value
            Object tmp = additions.get(name);
            String[] values = (tmp instanceof String[]) ? ((String[]) tmp) : (new String[] { (String) tmp });

            if ((ignoreType == IgnoreType.REQUEST_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("<input type=\"hidden\" name=\"");
                    buffer.append(name);
                    buffer.append("\" value=\"");
                    buffer.append(values[i]);
                    buffer.append("\" />");
                    buffer.append("\n");
                }
            }
        }

        return (buffer.toString());
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code>.
     * 
     * @see #makeQueryString( HttpServletRequest, Map, String[] )
     */
    public static String makeQueryString(HttpServletRequest request) {
        return (makeQueryString(request, new HashMap(), new String[0]));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> and key in
     * given <code>Map</code>.
     * 
     * @see #makeQueryString( HttpServletRequest, Map, String[] )
     */
    public static String makeQueryString(HttpServletRequest request, Map additions) {
        return (makeQueryString(request, additions, new String[0]));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> that is not
     * listed in the ignore list.
     * 
     * @see #makeQueryString( HttpServletRequest, Map, String[] )
     */
    public static String makeQueryString(HttpServletRequest request, String[] ignores) {
        return (makeQueryString(request, new HashMap(), ignores));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> and key in
     * given <code>Map</code> that is not listed in the ignore list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a mapping of strings to strings or string arrays to be
     *            included in the query string
     * @param ignores
     *            the list of parameters and map entries not to include
     * @return A string in the <em>x-www-form-urlencoded</em> format that is
     *         suitable for adding to a URL as a query string.
     */
    public static String makeQueryString(HttpServletRequest request, Map additions, String[] ignores) {
        return (makeQueryString(request, additions, ignores, IgnoreType.BOTH));
    }

    /**
     * Creates a query string of the format "key1=value1&amp;key2=value2" for
     * each parameter in the given <code>HttpServletRequest</code> and key in
     * given <code>Map</code> that is not listed in the ignore list.
     * 
     * @param request
     *            the <code>HttpServletRequest</code> to read the parameters
     *            from
     * @param additions
     *            a mapping of strings to strings or string arrays to be
     *            included in the query string
     * @param ignores
     *            the list of parameters and map entries not to include
     * @return A string in the <em>x-www-form-urlencoded</em> format that is
     *         suitable for adding to a URL as a query string.
     */
    public static String makeQueryString(HttpServletRequest request, Map additions, String[] ignores, IgnoreType ignoreType) {
        if (request == null || additions == null || ignores == null || ignoreType == null) {
            throw new IllegalArgumentException("Cannot take null parameters.");
        }

        StringBuffer buffer = new StringBuffer();

        ArrayList<String> ignoreList = new ArrayList<String>();
        for (int i = 0; i < ignores.length; i++) {
            ignoreList.add(ignores[i]);
        }

        Enumeration names = request.getParameterNames();

        while (names.hasMoreElements()) {
            String name = (String) names.nextElement();
            String[] values = request.getParameterValues(name);

            if ((ignoreType == IgnoreType.ADDITIONS_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("&");
                    buffer.append(name);
                    buffer.append("=");
                    buffer.append(Util.encode(values[i]));
                }
            }
        }

        Set keySet = additions.keySet();
        Iterator keys = keySet.iterator();

        while (keys.hasNext()) {
            String name = (String) keys.next();

            // handle both a String value or a String[] value
            Object tmp = additions.get(name);
            String[] values = (tmp instanceof String[]) ? ((String[]) tmp) : (new String[] { (String) tmp });

            if ((ignoreType == IgnoreType.REQUEST_ONLY || !ignoreList.contains(name)) && values != null) {
                for (int i = 0; i < values.length; i++) {
                    buffer.append("&");
                    buffer.append(name);
                    buffer.append("=");
                    buffer.append(Util.encode(values[i]));
                }
            }
        }

        // removes the first & from the buffer
        buffer.deleteCharAt(0);

        return (buffer.toString());
    }

    public static class IgnoreType extends Object {
        public static final int _REQUEST_ONLY = 0;

        public static final int _ADDITIONS_ONLY = 0;

        public static final int _BOTH = 0;

        public static final IgnoreType REQUEST_ONLY = new IgnoreType(_REQUEST_ONLY);

        public static final IgnoreType ADDITIONS_ONLY = new IgnoreType(_ADDITIONS_ONLY);

        public static final IgnoreType BOTH = new IgnoreType(_BOTH);

        protected int value;

        private IgnoreType(int value) {
            this.value = value;
        }

        public int getValue() {
            return this.value;
        }
    }

    public static Map<String, String> getOrderedMap(String names[][]) {
        TreeMap<String, String> orderedMap = new TreeMap<String, String>();

        for (int i = 0; i < names.length; i++) {
{'fraction_non_alphanumeric': 0.09901015889554572, 'fraction_numerical': 0.0066163063297733785, 'mean_word_length': 2.1636588380716932, 'pattern_counts': {'":': 0, '<': 164, '<?xml version=': 0, '>': 150, 'https://': 0, 'lorem ipsum': 0, 'www.': 14, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 8, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '9765', 'n_tokens_mistral': 10241, 'n_tokens_neox': 9763, 'n_words': 3508}