Package com.googlecode.gwt.test.internal.utils

Source Code of com.googlecode.gwt.test.internal.utils.GwtPropertiesHelper$SequenceReplacement

package com.googlecode.gwt.test.internal.utils;

import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Properties;

import com.googlecode.gwt.test.exceptions.GwtTestI18NException;
import com.googlecode.gwt.test.internal.AfterTestCallback;
import com.googlecode.gwt.test.internal.AfterTestCallbackManager;

/**
*
* Some .properties files utility methods. It enables the caching of resources. <strong>For internal
* use only.</strong>
*
* @author Bertrand Paquet
* @author Gael Lazzari
*
*/
public class GwtPropertiesHelper implements AfterTestCallback {

   /*
    * Read in a "logical line" from an InputStream/Reader, skip all comment and blank lines and
    * filter out those leading whitespace characters ( , and ) from the beginning of a
    * "natural line". Method returns the char length of the "logical line" and stores the line in
    * "lineBuf".
    */
   static class LineReader {
      byte[] inByteBuf;

      char[] inCharBuf;

      int inLimit = 0;
      int inOff = 0;
      InputStream inStream;
      char[] lineBuf = new char[1024];
      Reader reader;

      public LineReader(InputStream inStream) {
         this.inStream = inStream;
         inByteBuf = new byte[8192];
      }

      public LineReader(Reader reader) {
         this.reader = reader;
         inCharBuf = new char[8192];
      }

      int readLine() throws IOException {
         int len = 0;
         char c = 0;

         boolean skipWhiteSpace = true;
         boolean isCommentLine = false;
         boolean isNewLine = true;
         boolean appendedLineBegin = false;
         boolean precedingBackslash = false;
         boolean skipLF = false;

         while (true) {
            if (inOff >= inLimit) {
               inLimit = inStream == null ? reader.read(inCharBuf) : inStream.read(inByteBuf);
               inOff = 0;
               if (inLimit <= 0) {
                  if (len == 0 || isCommentLine) {
                     return -1;
                  }
                  return len;
               }
            }
            if (inStream != null) {
               // The line below is equivalent to calling a
               // ISO8859-1 decoder.
               c = (char) (0xff & inByteBuf[inOff++]);
            } else {
               c = inCharBuf[inOff++];
            }
            if (skipLF) {
               skipLF = false;
               if (c == '\n') {
                  continue;
               }
            }
            if (skipWhiteSpace) {
               if (c == ' ' || c == '\t' || c == '\f') {
                  continue;
               }
               if (!appendedLineBegin && (c == '\r' || c == '\n')) {
                  continue;
               }
               skipWhiteSpace = false;
               appendedLineBegin = false;
            }
            if (isNewLine) {
               isNewLine = false;
               if (c == '#' || c == '!') {
                  isCommentLine = true;
                  continue;
               }
            }

            if (c != '\n' && c != '\r') {
               lineBuf[len++] = c;
               if (len == lineBuf.length) {
                  int newLength = lineBuf.length * 2;
                  if (newLength < 0) {
                     newLength = Integer.MAX_VALUE;
                  }
                  char[] buf = new char[newLength];
                  System.arraycopy(lineBuf, 0, buf, 0, lineBuf.length);
                  lineBuf = buf;
               }
               // flip the preceding backslash flag
               if (c == '\\') {
                  precedingBackslash = !precedingBackslash;
               } else {
                  precedingBackslash = false;
               }
            } else {
               // reached EOL
               if (isCommentLine || len == 0) {
                  isCommentLine = false;
                  isNewLine = true;
                  skipWhiteSpace = true;
                  len = 0;
                  continue;
               }
               if (inOff >= inLimit) {
                  inLimit = inStream == null ? reader.read(inCharBuf) : inStream.read(inByteBuf);
                  inOff = 0;
                  if (inLimit <= 0) {
                     return len;
                  }
               }
               if (precedingBackslash) {
                  len -= 1;
                  // skip the leading whitespace characters in following line
                  skipWhiteSpace = true;
                  appendedLineBegin = true;
                  precedingBackslash = false;
                  if (c == '\r') {
                     skipLF = true;
                  }
               } else {
                  return len;
               }
            }
         }
      }
   }
   private static class SequenceReplacement {

      private final String regex;

      private final String to;

      public SequenceReplacement(String regex, String to) {
         this.regex = regex;
         this.to = to;
      }

      public String treat(String s) {
         return s.replaceAll(regex, to);
      }

   }

   private static final GwtPropertiesHelper INSTANCE = new GwtPropertiesHelper();

   public static GwtPropertiesHelper get() {
      return INSTANCE;
   }

   private final Map<String, Properties> cachedProperties;

   private final List<SequenceReplacement> sequenceReplacements;

   private GwtPropertiesHelper() {
      cachedProperties = new HashMap<String, Properties>();
      sequenceReplacements = new ArrayList<GwtPropertiesHelper.SequenceReplacement>();
      initSequenceReplacements();

      AfterTestCallbackManager.get().registerCallback(this);
   }

   public void afterTest() throws Throwable {
      // cachedProperties.clear();
      sequenceReplacements.clear();
      initSequenceReplacements();
   }

   public Properties getLocalizedProperties(String prefix, Locale locale) {
      if (locale != null) {
         prefix += "_" + locale.toString();
      }
      return getProperties(prefix);
   }

   public Properties getProperties(String path) {
      if (cachedProperties.containsKey(path)) {
         return cachedProperties.get(path);
      }
      String propertiesNameFile = "/" + path + ".properties";
      InputStream inputStream = path.getClass().getResourceAsStream(propertiesNameFile);
      if (inputStream == null) {
         cachedProperties.put(path, null);
         return null;
      }
      try {
         Properties properties = new Properties();
         InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "UTF-8");
         load(properties, inputStreamReader);
         cachedProperties.put(path, properties);
         return properties;
      } catch (Exception e) {
         throw new GwtTestI18NException("Unable to load property file [" + path + "]", e);
      }
   }

   public void replaceSequence(String regex, String to) {
      sequenceReplacements.add(new SequenceReplacement(regex, to));
   }

   public String treatString(String string) {
      for (SequenceReplacement sequenceReplacement : sequenceReplacements) {
         string = sequenceReplacement.treat(string);
      }

      return string;
   }

   private void initSequenceReplacements() {
      // hardcoded to fix gwt "bug"
      sequenceReplacements.add(new SequenceReplacement("\\u00A0", " "));
   }

   /**
    * Method copied from JDK 1.6 Properties.load(Reader)..
    *
    * @param properties
    * @param reader
    * @throws IOException
    */
   private synchronized void load(Properties properties, Reader reader) throws IOException {
      load0(properties, new LineReader(reader));
   }

   private void load0(Properties properties, LineReader lr) throws IOException {
      char[] convtBuf = new char[1024];
      int limit;
      int keyLen;
      int valueStart;
      char c;
      boolean hasSep;
      boolean precedingBackslash;

      while ((limit = lr.readLine()) >= 0) {
         c = 0;
         keyLen = 0;
         valueStart = limit;
         hasSep = false;

         precedingBackslash = false;
         while (keyLen < limit) {
            c = lr.lineBuf[keyLen];
            // need check if escaped.
            if ((c == '=' || c == ':') && !precedingBackslash) {
               valueStart = keyLen + 1;
               hasSep = true;
               break;
            } else if ((c == ' ' || c == '\t' || c == '\f') && !precedingBackslash) {
               valueStart = keyLen + 1;
               break;
            }
            if (c == '\\') {
               precedingBackslash = !precedingBackslash;
            } else {
               precedingBackslash = false;
            }
            keyLen++;
         }
         while (valueStart < limit) {
            c = lr.lineBuf[valueStart];
            if (c != ' ' && c != '\t' && c != '\f') {
               if (!hasSep && (c == '=' || c == ':')) {
                  hasSep = true;
               } else {
                  break;
               }
            }
            valueStart++;
         }
         String key = loadConvert(lr.lineBuf, 0, keyLen, convtBuf);
         String value = loadConvert(lr.lineBuf, valueStart, limit - valueStart, convtBuf);
         properties.put(key, value);
      }
   }

   /*
    * Converts encoded &#92;uxxxx to unicode chars and changes special saved chars to their original
    * forms
    */
   private String loadConvert(char[] in, int off, int len, char[] convtBuf) {
      if (convtBuf.length < len) {
         int newLen = len * 2;
         if (newLen < 0) {
            newLen = Integer.MAX_VALUE;
         }
         convtBuf = new char[newLen];
      }
      char aChar;
      char[] out = convtBuf;
      int outLen = 0;
      int end = off + len;

      while (off < end) {
         aChar = in[off++];
         if (aChar == '\\') {
            aChar = in[off++];
            if (aChar == 'u') {
               // Read the xxxx
               int value = 0;
               for (int i = 0; i < 4; i++) {
                  aChar = in[off++];
                  switch (aChar) {
                     case '0':
                     case '1':
                     case '2':
                     case '3':
                     case '4':
                     case '5':
                     case '6':
                     case '7':
                     case '8':
                     case '9':
                        value = (value << 4) + aChar - '0';
                        break;
                     case 'a':
                     case 'b':
                     case 'c':
                     case 'd':
                     case 'e':
                     case 'f':
                        value = (value << 4) + 10 + aChar - 'a';
                        break;
                     case 'A':
                     case 'B':
                     case 'C':
                     case 'D':
                     case 'E':
                     case 'F':
                        value = (value << 4) + 10 + aChar - 'A';
                        break;
                     default:
                        throw new IllegalArgumentException("Malformed \\uxxxx encoding.");
                  }
               }
               out[outLen++] = (char) value;
            } else {
               if (aChar == 't') {
                  aChar = '\t';
               } else if (aChar == 'r') {
                  aChar = '\r';
               } else if (aChar == 'n') {
                  aChar = '\n';
               } else if (aChar == 'f') {
                  aChar = '\f';
               }
               out[outLen++] = aChar;
            }
         } else {
            out[outLen++] = aChar;
         }
      }
      String line = new String(out, 0, outLen);

      // hack of the JDK 6 function
      return treatString(line);

   }

}
TOP

Related Classes of com.googlecode.gwt.test.internal.utils.GwtPropertiesHelper$SequenceReplacement

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.