/*******************************************************************************
 * Copyright (c) 2000, 2004 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/

package org.eclipse.jst.ws.internal.common;

import java.io.IOException;
import java.io.InputStream;
import java.util.Enumeration;
import java.util.Vector;
import org.eclipse.jdt.core.JavaConventions;

/**
  * This class contains some useful string utilities that are not provided by
  * either String or StringBuffer.
  *
  * @author Peter Moogk
  * @date   July 13, 2000
**/
public final class StringUtils
{

  // Copyright
  public static final String copyright = "(c) Copyright IBM Corporation 2000, 2002.";

  /**
  * The platform-specific line separator.
  */
  public static final String NEWLINE = System.getProperty("line.separator");

  private StringUtils(){};

  /**
    * This method splits a single line of text into multiple lines
    * based on a maximum line length.  The method will try to fit as
    * many words as possible onto a line without exceeding the maximum
    * line length.  Note: the only case where a line might exceed the
    * maximum is if a single word is longer than the maximum.
  **/
  public static String[] splitter( String text, int max_length )
  {
    Vector          return_text = new Vector(20);
    String[]        return_str;
    int             index = 0;

    while( index < text.length() )
    {
      String str = text.substring( index, Math.min( max_length + index,
                                                    text.length() ) );
      int space_index = str.lastIndexOf( " " );

      if( index + str.length() < text.length() &&
          text.charAt( index + str.length() - 1 ) != ' ' &&
          text.charAt( index + str.length() ) != ' ' &&
          space_index != -1 )
      {
        return_text.addElement( str.substring( 0, space_index ) );
        index += space_index + 1;
      }
      else
      {
        return_text.addElement( str.trim() );
        index += str.length();
      }
    }

    return_str = new String[return_text.size()];

    for( index = 0; index < return_text.size(); index++ )
    {
      return_str[index] = (String)(return_text.elementAt(index));
    }

    return return_str;
  }

  /**
    * This method returns a string with a repeated number of characters.
  **/
  static public String repeat( char the_char, int count )
  {
    StringBuffer buf = new StringBuffer( count );

    for( int index = 0; index < count; index++ )
    {
      buf.append( the_char );
    }

    return buf.toString();
  }

  /**
    * This method flattens an array of arguments to a string.
    * The method respects embedded whitespace and quotes.
    * <ul>
    * <li>Any argument with embedded whitespace will be flattened out
    * with enclosing quotes. For example, the single argument
    * <u>Hello World</u>
    * will be returned as
    * <u>"Hello World"</u>.
    * <li>Any argument with quotes will be flattened out with the
    * quotes escaped. For example, the single argument
    * <u>"Happy days"</u>
    * will be returned as
    * <u>\"Happy days\"</u>.
    * </ul>
    * @param arguments The array of strings to flatten.
    * @return the flattened string.
  */
  static public String flattenArguments ( String[] arguments )
  {
    StringBuffer buf = new StringBuffer();

    for (int i=0; i<arguments.length; i++)
    {
      //
      // Append a separator (except the first time).
      //
      if (i > 0) buf.append(' ');

      //
      // Look for whitespace.
      //
      boolean whitespace = false;
      char[] chars = arguments[i].toCharArray();
      for (int j=0; !whitespace && j<chars.length; j++)
      {
        if (Character.isWhitespace(chars[j]))
        {
          whitespace = true;
        }
      }

      //
      // Append the argument, quoted as necessary.
      //
      if (whitespace) buf.append('"');
      for (int j=0; j<chars.length; j++)
      {
        if (chars[j] == '"') buf.append('\\');
        buf.append(chars[j]);
      }
      if (whitespace) buf.append('"');
    }

    return buf.toString();
  }

  /**
    * This method parses whitespace-delimitted filenames from
    * the given <code>input</code> stream. <b>Limitation:</b>
    * Quoted filenames or filenames with embedded whitespace
    * are not currently supported.
    * @param input The input stream.
    * @return An enumeration of filenames from the stream.
  */
  static public Enumeration parseFilenamesFromStream ( InputStream input )
  throws IOException
  {
    Vector filenames = new Vector(64,64);
    StringBuffer buffer = null;
    byte state = STATE_WS;
    int ic = input.read();
    while (ic >= 0)
    {
      char c = (char)ic;
      switch (state)
      {
        case STATE_WS:
          if (!Character.isWhitespace(c))
          {
            buffer = new StringBuffer();
            buffer.append(c);
            state = STATE_NWS;
          }
          break;
        case STATE_NWS:
          if (!Character.isWhitespace(c))
          {
            buffer.append(c);
          }
          else
          {
            String filename = buffer.toString();
            filenames.add(filename);
            buffer = null;
            state = STATE_WS;
          }
          break;
        default:
          break;
      }
      ic = input.read();
    }
    return filenames.elements();
  }

  private static final byte STATE_WS = 0;
  private static final byte STATE_NWS = 1;


  /**
  * Returns true is the type passed in is a primtive java type
  * @param class name String
  * @return true is primitive type
  */
  public static boolean isPrimitiveType(String typeName) 
  {

    if (typeName.equalsIgnoreCase("boolean") ||
      typeName.equalsIgnoreCase("byte") ||
      typeName.equalsIgnoreCase("double") ||
      typeName.equalsIgnoreCase("float") ||
      typeName.equalsIgnoreCase("int") ||
      typeName.equalsIgnoreCase("long") ||
      typeName.equalsIgnoreCase("short") ||
      typeName.equalsIgnoreCase("char"))
      return true;
    return false;

  }

  /**
  * The method replace the characters that are allowed in URIs
  * and not allowed in Java class names to an underscore ('_')
  * @param URI String
  * @return valid Java class name String
  */
  public static String URI2ClassName( String uri ) {
    String className = uri;
    for ( int i = 0; i < URI_SYMBOLS.length; i++ ) {
    	className = className.replace ( URI_SYMBOLS[i], UNDERSCORE );
    }
    return className;
  }

  private static final char[] URI_SYMBOLS = {'-', '~', '#', '/', '.'};
  private static final char UNDERSCORE = '_';


  /**
   * This returns a valid Java identifier based on the given name. 
   * (follows JAX-RPC 1.0 Public Review Draft 2 recommendations)
   */
  public static String javaIdentifierFor(String localName)
  {
    StringBuffer result = new StringBuffer();
    boolean skipped = false;
    for (int i = 0, length = localName.length(); i < length; ++i)
    {
      char character = localName.charAt(i);
      if (Character.isJavaIdentifierPart(character) && !isDelimiter(character))
      {
        if (skipped && result.length() != 0)
        {
          character = Character.toUpperCase(character);
        }
        result.append(character);
        skipped = false;
      }
      else
      {
        skipped =true;
      }
    }

    if (!JavaConventions.validateIdentifier(result.toString()).isOK())
    {
      result.insert(0, "_");
    }

    return result.toString();
  }

  private static boolean isDelimiter(char character)
  {
    return "\u002D\u002E\u003A\u005F\u00B7\u0387\u06DD\u06DE".indexOf(character) != -1;
  }
  
  
}
