You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sis.apache.org by de...@apache.org on 2014/04/14 05:32:31 UTC

svn commit: r1587131 - in /sis/branches/JDK7: ./ core/sis-referencing/src/main/java/org/apache/sis/parameter/ core/sis-utility/src/main/java/org/apache/sis/internal/jdk8/ core/sis-utility/src/main/java/org/apache/sis/internal/util/ core/sis-utility/src...

Author: desruisseaux
Date: Mon Apr 14 03:32:30 2014
New Revision: 1587131

URL: http://svn.apache.org/r1587131
Log:
Merge from the JDK7 branch.

Added:
    sis/branches/JDK7/src/main/rdf/
      - copied from r1587128, sis/branches/JDK8/src/main/rdf/
    sis/branches/JDK7/storage/sis-netcdf/src/test/java/org/apache/sis/internal/netcdf/impl/AttributeTest.java
      - copied unchanged from r1587128, sis/branches/JDK8/storage/sis-netcdf/src/test/java/org/apache/sis/internal/netcdf/impl/AttributeTest.java
Removed:
    sis/branches/JDK7/core/sis-utility/src/test/java/org/apache/sis/internal/jdk8/
Modified:
    sis/branches/JDK7/   (props changed)
    sis/branches/JDK7/core/sis-referencing/src/main/java/org/apache/sis/parameter/TensorParameters.java
    sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/jdk8/JDK8.java
    sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/util/Utilities.java
    sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/collection/WeakHashSet.java
    sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/logging/LoggerAdapter.java
    sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/xml/FilteredNamespaces.java
    sis/branches/JDK7/core/sis-utility/src/test/java/org/apache/sis/test/suite/UtilityTestSuite.java
    sis/branches/JDK7/pom.xml
    sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/Variable.java
    sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/Attribute.java
    sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/ChannelDecoder.java
    sis/branches/JDK7/storage/sis-netcdf/src/test/java/org/apache/sis/test/suite/NetcdfTestSuite.java

Propchange: sis/branches/JDK7/
------------------------------------------------------------------------------
  Merged /sis/branches/JDK8:r1585799-1587128

Modified: sis/branches/JDK7/core/sis-referencing/src/main/java/org/apache/sis/parameter/TensorParameters.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-referencing/src/main/java/org/apache/sis/parameter/TensorParameters.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-referencing/src/main/java/org/apache/sis/parameter/TensorParameters.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-referencing/src/main/java/org/apache/sis/parameter/TensorParameters.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -105,6 +105,7 @@ import java.util.Objects;
  * @version 0.4
  * @module
  */
+@SuppressWarnings("unchecked")
 public class TensorParameters<E> implements Serializable {
     /**
      * Serial number for inter-operability with different versions.
@@ -206,7 +207,7 @@ public class TensorParameters<E> impleme
      *                    Length may be different if the caller wants to generalize usage of this class to tensors.
      */
     @SafeVarargs
-    @SuppressWarnings({"unchecked", "rawtypes"})
+    @SuppressWarnings("rawtypes")
     public TensorParameters(final Class<E> elementType, final String prefix, final String separator,
             final ParameterDescriptor<Integer>... dimensions)
     {
@@ -234,7 +235,7 @@ public class TensorParameters<E> impleme
      *
      * <p>This method is invoked by constructor and on deserialization.</p>
      */
-    @SuppressWarnings({"unchecked", "rawtypes"})
+    @SuppressWarnings("rawtypes")
     private <T> ParameterDescriptor<T>[] createCache() {
         if (Number.class.isAssignableFrom(elementType)) try {
             one  = (E) Numbers.wrap(1, (Class) elementType);

Modified: sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/jdk8/JDK8.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/jdk8/JDK8.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/jdk8/JDK8.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/jdk8/JDK8.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -23,7 +23,6 @@ import java.util.Locale;
 import java.util.TimeZone;
 import java.util.concurrent.atomic.AtomicReference;
 import javax.xml.bind.DatatypeConverter;
-import org.apache.sis.util.CharSequences;
 
 
 /**
@@ -32,7 +31,7 @@ import org.apache.sis.util.CharSequences
  *
  * @author  Martin Desruisseaux (Geomatys)
  * @since   0.3
- * @version 0.4
+ * @version 0.5
  * @module
  */
 public final class JDK8 {
@@ -63,101 +62,18 @@ public final class JDK8 {
 
     /**
      * Parses a date from a string in ISO 8601 format. More specifically, this method expects the
-     * format defined by <cite>XML Schema Part 2: Datatypes for {@code xsd:dateTime}</cite>, with
-     * some additional flexibility (e.g. missing minutes or seconds fields are automatically added).
+     * format defined by <cite>XML Schema Part 2: Datatypes for {@code xsd:dateTime}</cite>.
      *
      * <p>This method will be replaced by {@link java.time.format.DateTimeFormatter} on the JDK8 branch.</p>
      *
-     * @param  date The date to parse, or {@code null}.
-     * @param  defaultToUTC {@code true} if the default timezone shall be UTL, or {@code false} for locale default.
-     * @return The parsed date, or {@code null} if the given string was {@code null}.
+     * @param  date The date to parse.
+     * @return The parsed date.
      * @throws IllegalArgumentException if the given date can not be parsed.
      *
      * @see DatatypeConverter#parseDateTime(String)
      */
-    public static Date parseDateTime(String date, final boolean defaultToUTC) throws IllegalArgumentException {
-        if (date != null) {
-            date = CharSequences.trimWhitespaces(date);
-            if (!date.isEmpty()) {
-                /*
-                 * Check for missing time fields and time zone. For example if the given date is
-                 * "2005-09-22T00:00", then this block will complete it as "2005-09-22T00:00:00".
-                 * In addition, a 'Z' suffix will be appended if 'defaultToUTC' is true.
-                 */
-                int timeFieldStart  = date.lastIndexOf('T') + 1; // 0 if there is no time field.
-                int timeFieldEnd    = date.length();             // To be updated if there is a time field.
-                int missingFields   = 0;                         // Number of missing time fields.
-                boolean hasTimeZone = date.charAt(timeFieldEnd - 1) == 'Z';
-                if (timeFieldStart != 0) {
-                    if (hasTimeZone) {
-                        timeFieldEnd--;
-                    } else {
-                        final int s = Math.max(date.indexOf('+', timeFieldStart),
-                                               date.indexOf('-', timeFieldStart));
-                        hasTimeZone = (s >= 0);
-                        if (hasTimeZone) {
-                            timeFieldEnd = s;
-                        }
-                    }
-                    missingFields = 2;
-                    for (int i=timeFieldStart; i<timeFieldEnd; i++) {
-                        if (date.charAt(i) == ':') {
-                            if (--missingFields == 0) break;
-                        }
-                    }
-                }
-                /*
-                 * At this point, we have determined if there is some missing fields.
-                 * The timezone will be considered missing only if 'defaultToUTC' is true.
-                 */
-                CharSequence modified = date;
-                hasTimeZone |= !defaultToUTC;
-                if (missingFields != 0 || !hasTimeZone) {
-                    final StringBuilder buffer = new StringBuilder(date);
-                    while (--missingFields >= 0) {
-                        buffer.append(":00");
-                    }
-                    if (!hasTimeZone) {
-                        buffer.append('Z');
-                    }
-                    modified = buffer;
-                }
-                /*
-                 * Now ensure that all numbers have at least two digits.
-                 */
-                int indexOfLastDigit = 0;
-                for (int i=modified.length(); --i >= 0;) {
-                    char c = modified.charAt(i);
-                    final boolean isDigit = (c >= '0' && c <= '9'); // Do not use Character.isDigit(char).
-                    if (indexOfLastDigit == 0) {
-                        // We were not scaning a number. Check if we are now starting doing so.
-                        if (isDigit) {
-                            indexOfLastDigit = i;
-                        }
-                    } else {
-                        // We were scaning a number. Check if we found the begining.
-                        if (!isDigit) {
-                            if (indexOfLastDigit - i == 1) {
-                                // Reuse the buffer if it exists, or create a new one otherwise.
-                                final StringBuilder buffer;
-                                if (modified == date) {
-                                    modified = buffer = new StringBuilder(date);
-                                } else {
-                                    buffer = (StringBuilder) modified;
-                                }
-                                buffer.insert(i+1, '0');
-                            }
-                            indexOfLastDigit = 0;
-                        }
-                    }
-                }
-                /*
-                 * Now delegate to the utility method provided in the JAXB packages.
-                 */
-                return DatatypeConverter.parseDateTime(modified.toString()).getTime();
-            }
-        }
-        return null;
+    public static Date parseDateTime(final String date) throws IllegalArgumentException {
+        return DatatypeConverter.parseDateTime(date).getTime();
     }
 
     /**
@@ -166,15 +82,12 @@ public final class JDK8 {
      *
      * <p>This method will be replaced by {@link java.time.format.DateTimeFormatter} on the JDK8 branch.</p>
      *
-     * @param  date The date to format, or {@code null}.
-     * @return The formatted date, or {@code null} if the given date was null.
+     * @param  date The date to format.
+     * @return The formatted date.
      *
      * @see DatatypeConverter#printDateTime(Calendar)
      */
     public static String printDateTime(final Date date) {
-        if (date == null) {
-            return null;
-        }
         Calendar calendar = CALENDAR.getAndSet(null);
         if (calendar == null) {
             calendar = new GregorianCalendar(TimeZone.getTimeZone("UTC"), Locale.US);

Modified: sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/util/Utilities.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/util/Utilities.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/util/Utilities.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/internal/util/Utilities.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -91,7 +91,7 @@ public final class Utilities extends Sta
      * used mostly for debugging purpose.
      *
      * @param  classe     The class to format.
-     * @param  properties The (<var>key</var>=</var>value</var>) pairs.
+     * @param  properties The (<var>key</var>=<var>value</var>) pairs.
      * @return A string representation of an instance of the given class having the given properties.
      *
      * @since 0.4

Modified: sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/collection/WeakHashSet.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/collection/WeakHashSet.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/collection/WeakHashSet.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/collection/WeakHashSet.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -182,22 +182,17 @@ public class WeakHashSet<E> extends Abst
 
     /**
      * Checks if this {@code WeakHashSet} is valid. This method counts the number of elements and
-     * compares it to {@link #count}. If the check fails, the number of elements is corrected (if
-     * we didn't, an {@link AssertionError} would be thrown for every operations after the first
-     * error, which make debugging more difficult). The set is otherwise unchanged, which should
-     * help to get similar behavior as if assertions hasn't been turned on.
+     * compares it to {@link #count}. This method is invoked in assertions only.
      */
     @Debug
     private boolean isValid() {
-        assert Thread.holdsLock(this);
-        assert count <= upperCapacityThreshold(table.length);
-        final int n = count(table);
-        if (n != count) {
-            count = n;
-            return false;
-        } else {
-            return true;
+        if (!Thread.holdsLock(this)) {
+            throw new AssertionError();
         }
+        if (count > upperCapacityThreshold(table.length)) {
+            throw new AssertionError(count);
+        }
+        return count(table) == count;
     }
 
     /**
@@ -370,12 +365,12 @@ public class WeakHashSet<E> extends Abst
         @SuppressWarnings("unchecked")
         final E[] elements = (E[]) Array.newInstance(elementType, count);
         int index = 0;
-        final Entry[] table = this.table;
-        for (int i=0; i<table.length; i++) {
-            for (Entry el=table[i]; el!=null; el=(Entry) el.next) {
+        for (Entry el : table) {
+            while (el != null) {
                 if ((elements[index] = el.get()) != null) {
                     index++;
                 }
+                el = (Entry) el.next;
             }
         }
         return ArraysExt.resize(elements, index);

Modified: sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/logging/LoggerAdapter.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/logging/LoggerAdapter.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/logging/LoggerAdapter.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/util/logging/LoggerAdapter.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -71,7 +71,7 @@ import org.apache.sis.util.Debug;
  * behavior since their configuration is entirely contained in the external logging framework.
  *
  * {@section Localization}
- * This logger is always created without resource bundles. Localizations must be performed through
+ * This logger is always created without resource bundles. Localizations shall be done through
  * explicit calls to {@code logrb} or {@link #log(LogRecord)} methods. This is sufficient for
  * SIS needs, which performs all localizations through the later. Note that those methods
  * will be slower in this {@code LoggerAdapter} than the default {@link Logger} because this
@@ -87,7 +87,7 @@ import org.apache.sis.util.Debug;
  *
  * @author  Martin Desruisseaux (IRD, Geomatys)
  * @since   0.3 (derived from geotk-2.4)
- * @version 0.3
+ * @version 0.5
  * @module
  *
  * @see Logging
@@ -352,8 +352,9 @@ public abstract class LoggerAdapter exte
     }
 
     /**
-     * Logs a record. The default implementation delegates to
-     * {@link #logrb(Level,String,String,String,String,Object[]) logrb}.
+     * Logs a record. The default implementation delegates to one of the
+     * {@link #logrb(Level,String,String,ResourceBundle,String,Object[]) logrb} or
+     * {@link #logp(Level,String,String,String)} methods.
      *
      * @param record The log record to be published.
      */
@@ -369,37 +370,34 @@ public abstract class LoggerAdapter exte
         if (filter != null && !filter.isLoggable(record)) {
             return;
         }
-        Level     level        = record.getLevel();
-        String    sourceClass  = record.getSourceClassName();
-        String    sourceMethod = record.getSourceMethodName();
-        String    bundleName   = record.getResourceBundleName();
-        String    message      = record.getMessage();
-        Object[]  params       = record.getParameters();
-        Throwable thrown       = record.getThrown();
-        ResourceBundle bundle  = record.getResourceBundle();
-        boolean   localized    = false;
-        if (bundle != null) try {
-            message   = bundle.getString(message);
-            localized = true; // Sets only if the above succeed.
-        } catch (MissingResourceException e) {
-            // The default Formatter.messageFormat implementation ignores this exception
-            // and uses the bundle key as the message, so we mimic its behavior here.
-        }
+        final Level     level        = record.getLevel();
+        final String    sourceClass  = record.getSourceClassName();
+        final String    sourceMethod = record.getSourceMethodName();
+        final String    message      = record.getMessage();
+        final Object[]  params       = record.getParameters();
+        final Throwable thrown       = record.getThrown();
+        final ResourceBundle bundle  = record.getResourceBundle();
         final boolean useThrown = (thrown != null) && (params == null || params.length == 0);
-        if (localized) {
-            // The message is already localized.
+        if (bundle != null) {
             if (useThrown) {
-                logp(level, sourceClass, sourceMethod, message, thrown);
+                logrb(level, sourceClass, sourceMethod, bundle, message, thrown);
             } else {
-                logp(level, sourceClass, sourceMethod, message, params);
+                logrb(level, sourceClass, sourceMethod, bundle, message, params);
             }
         } else {
-            // The message needs to be localized. The bundle was null but maybe bundleName is not.
-            // Futhermore subclass may have overridden the 'logrb' methods.
-            if (useThrown) {
-                logrb(level, sourceClass, sourceMethod, bundleName, message, thrown);
+            final String bundleName = record.getResourceBundleName();
+            if (bundleName != null) {
+                if (useThrown) {
+                    logrb(level, sourceClass, sourceMethod, bundleName, message, thrown);
+                } else {
+                    logrb(level, sourceClass, sourceMethod, bundleName, message, params);
+                }
             } else {
-                logrb(level, sourceClass, sourceMethod, bundleName, message, params);
+                if (useThrown) {
+                    logp(level, sourceClass, sourceMethod, message, thrown);
+                } else {
+                    logp(level, sourceClass, sourceMethod, message, params);
+                }
             }
         }
     }
@@ -558,6 +556,46 @@ public abstract class LoggerAdapter exte
 
     /**
      * Logs a localizable record at the specified level. The default implementation localizes the
+     * message immediately, then delegates to <code>{@linkplain #logp(Level,String,String,String,
+     * Object[]) logp}(level, sourceClass, sourceMethod, message, params)</code>.
+     *
+     * @param level        One of the message level identifiers.
+     * @param sourceClass  Name of class that issued the logging request.
+     * @param sourceMethod Name of the method.
+     * @param bundle       The resource bundle for localizing the message, or {@code null}.
+     * @param message      The message to log.
+     * @param params       Array of parameters to the method being entered.
+     *
+     * @since 0.5
+     */
+    public void logrb(final Level level, final String sourceClass, final String sourceMethod,
+                      final ResourceBundle bundle, final String message, final Object... params)
+    {
+        logp(level, sourceClass, sourceMethod, localize(bundle, message), params);
+    }
+
+    /**
+     * Logs a localizable record at the specified level. The default implementation localizes the
+     * message immediately, then delegates to <code>{@linkplain #logp(Level,String,String,String,
+     * Throwable) logp}(level, sourceClass, sourceMethod, message, thrown)</code>.
+     *
+     * @param level        One of the message level identifiers.
+     * @param sourceClass  Name of class that issued the logging request.
+     * @param sourceMethod Name of the method.
+     * @param bundle       The resource bundle for localizing the message, or {@code null}.
+     * @param message      The message to log.
+     * @param thrown       Throwable associated with log message.
+     *
+     * @since 0.5
+     */
+    public void logrb(final Level level, final String sourceClass, final String sourceMethod,
+                      final ResourceBundle bundle, final String message, final Throwable thrown)
+    {
+        logp(level, sourceClass, sourceMethod, localize(bundle, message), thrown);
+    }
+
+    /**
+     * Logs a localizable record at the specified level. The default implementation localizes the
      * message immediately, then delegates to <code>{@linkplain #logp(Level,String,String,String)
      * logp}(level, sourceClass, sourceMethod, message)</code>.
      *
@@ -566,8 +604,11 @@ public abstract class LoggerAdapter exte
      * @param sourceMethod Name of the method.
      * @param bundleName   Name of resource bundle to localize message, or {@code null}.
      * @param message      The message to log.
+     *
+     * @deprecated JDK 8 has deprecated this method.
      */
     @Override
+    @Deprecated
     public void logrb(final Level level, final String sourceClass, final String sourceMethod,
                       final String bundleName, final String message)
     {
@@ -585,8 +626,11 @@ public abstract class LoggerAdapter exte
      * @param bundleName   Name of resource bundle to localize message, or {@code null}.
      * @param message      The message to log.
      * @param thrown       Throwable associated with log message.
+     *
+     * @deprecated JDK 8 has deprecated this method.
      */
     @Override
+    @Deprecated
     public void logrb(final Level level, final String sourceClass, final String sourceMethod,
                       final String bundleName, final String message, final Throwable thrown)
     {
@@ -604,8 +648,11 @@ public abstract class LoggerAdapter exte
      * @param bundleName   Name of resource bundle to localize message, or {@code null}.
      * @param message      The message to log.
      * @param param        Parameter to the method being entered.
+     *
+     * @deprecated JDK 8 has deprecated this method.
      */
     @Override
+    @Deprecated
     public void logrb(final Level level, final String sourceClass, final String sourceMethod,
                       final String bundleName, final String message, final Object param)
     {
@@ -623,10 +670,13 @@ public abstract class LoggerAdapter exte
      * @param bundleName   Name of resource bundle to localize message, or {@code null}.
      * @param message      The message to log.
      * @param params       Array of parameters to the method being entered.
+     *
+     * @deprecated JDK 8 has deprecated this method.
      */
     @Override
+    @Deprecated
     public void logrb(final Level level, final String sourceClass, final String sourceMethod,
-                      final String bundleName, String message, final Object[] params)
+                      final String bundleName, final String message, final Object[] params)
     {
         logp(level, sourceClass, sourceMethod, localize(bundleName, message), params);
     }
@@ -724,4 +774,18 @@ public abstract class LoggerAdapter exte
         }
         return message;
     }
+
+    /**
+     * Localizes the specified message. This is a helper method for
+     * {@code logrb(...)} methods that delegate their work to {@code logp(...)}
+     */
+    private static String localize(final ResourceBundle bundle, String message) {
+        if (bundle != null) try {
+            message = bundle.getString(message);
+        } catch (MissingResourceException e) {
+            // The default Formatter.messageFormat implementation ignores this exception
+            // and uses the bundle key as the message, so we mimic its behavior here.
+        }
+        return message;
+    }
 }

Modified: sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/xml/FilteredNamespaces.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/xml/FilteredNamespaces.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/xml/FilteredNamespaces.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-utility/src/main/java/org/apache/sis/xml/FilteredNamespaces.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -143,6 +143,7 @@ final class FilteredNamespaces implement
      * Returns all prefixes for the given namespace.
      */
     @Override
+    @SuppressWarnings("unchecked")
     public Iterator<String> getPrefixes(final String namespaceURI) {
         return context.getPrefixes(toImpl(namespaceURI));
     }

Modified: sis/branches/JDK7/core/sis-utility/src/test/java/org/apache/sis/test/suite/UtilityTestSuite.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/core/sis-utility/src/test/java/org/apache/sis/test/suite/UtilityTestSuite.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/core/sis-utility/src/test/java/org/apache/sis/test/suite/UtilityTestSuite.java [UTF-8] (original)
+++ sis/branches/JDK7/core/sis-utility/src/test/java/org/apache/sis/test/suite/UtilityTestSuite.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -36,7 +36,6 @@ import org.junit.BeforeClass;
     org.apache.sis.internal.test.XMLComparatorTest.class,
 
     // Most basic functions of SIS library.
-    org.apache.sis.internal.jdk8.JDK8Test.class,
     org.apache.sis.internal.util.NumericsTest.class,
     org.apache.sis.setup.OptionKeyTest.class,
     org.apache.sis.util.ArraysExtTest.class,

Modified: sis/branches/JDK7/pom.xml
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/pom.xml?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/pom.xml (original)
+++ sis/branches/JDK7/pom.xml Mon Apr 14 03:32:30 2014
@@ -405,7 +405,7 @@ Apache SIS is a free software, Java lang
     <!-- Following properties are branch-specific -->
     <maven.compile.source>1.7</maven.compile.source>
     <maven.compile.target>1.7</maven.compile.target>
-    <sis.plugin.version>0.4</sis.plugin.version>
+    <sis.plugin.version>${project.version}</sis.plugin.version>
     <geoapi.version>3.1-SNAPSHOT</geoapi.version>
   </properties>
 
@@ -435,6 +435,9 @@ Apache SIS is a free software, Java lang
           <source>${maven.compile.source}</source>
           <target>${maven.compile.target}</target>
           <encoding>${project.build.sourceEncoding}</encoding>
+          <compilerArgs>
+            <arg>-Xlint:all</arg>
+          </compilerArgs>
         </configuration>
       </plugin>
 

Modified: sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/Variable.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/Variable.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/Variable.java [UTF-8] (original)
+++ sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/Variable.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -206,6 +206,8 @@ public abstract class Variable {
 
     /**
      * Returns a string representation of this variable for debugging purpose.
+     *
+     * @return A string representation of this variable.
      */
     @Debug
     @Override

Modified: sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/Attribute.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/Attribute.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/Attribute.java [UTF-8] (original)
+++ sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/Attribute.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -19,6 +19,7 @@ package org.apache.sis.internal.netcdf.i
 import java.lang.reflect.Array;
 import org.apache.sis.util.Debug;
 import org.apache.sis.util.Utilities;
+import org.apache.sis.util.CharSequences;
 
 // Related to JDK8
 import org.apache.sis.internal.jdk8.Function;
@@ -30,7 +31,7 @@ import org.apache.sis.internal.jdk8.Func
  * @author  Johann Sorel (Geomatys)
  * @author  Martin Desruisseaux (Geomatys)
  * @since   0.3
- * @version 0.3
+ * @version 0.5
  * @module
  */
 final class Attribute {
@@ -101,6 +102,99 @@ final class Attribute {
     }
 
     /**
+     * Modifies, if needed, the given date in order to make it compliant with the ISO 8601 format.
+     * For example missing minutes or seconds fields are automatically added. The intend is to turn
+     * a NetCDF date into something parseable by {@code java.util.time} or {@code javax.xml.bind}.
+     *
+     * @param  date The date to parse, or {@code null}.
+     * @return The date modified if needed or {@code null} if the given string was {@code null}.
+     *
+     * @since 0.5 (derived from 0.3)
+     */
+    static String dateToISO(String date) {
+        date = CharSequences.trimWhitespaces(date);
+        if (date != null && !date.isEmpty()) {
+            /*
+             * Check for missing time fields and time zone. For example if the given date is
+             * "2005-09-22T00:00", then this block will complete it as "2005-09-22T00:00:00".
+             * In addition, a 'Z' suffix will be appended if 'defaultToUTC' is true.
+             */
+            int timeFieldStart  = date.lastIndexOf('T') + 1; // 0 if there is no time field.
+            int timeFieldEnd    = date.length();             // To be updated if there is a time field.
+            int missingFields   = 2;                         // Number of missing time fields.
+            boolean hasTimeZone = date.charAt(timeFieldEnd - 1) == 'Z';
+            if (timeFieldStart != 0) {
+                if (hasTimeZone) {
+                    timeFieldEnd--;
+                } else {
+                    final int s = Math.max(date.indexOf('+', timeFieldStart),
+                                           date.indexOf('-', timeFieldStart));
+                    if (hasTimeZone = (s >= 0)) {
+                        timeFieldEnd = s;
+                    }
+                }
+                for (int i=timeFieldStart; i<timeFieldEnd; i++) {
+                    if (date.charAt(i) == ':') {
+                        if (--missingFields == 0) break;
+                    }
+                }
+            }
+            /*
+             * If we have determined that there is some missing time fields,
+             * append default values for them.
+             */
+            CharSequence modified = date;
+            if (missingFields != 0 || !hasTimeZone) {
+                final StringBuilder buffer = new StringBuilder(date);
+                buffer.setLength(timeFieldEnd);
+                if (timeFieldStart == 0) {
+                    buffer.append("T00");
+                }
+                while (--missingFields >= 0) {
+                    buffer.append(":00");
+                }
+                if (hasTimeZone) {
+                    buffer.append(date, timeFieldEnd, date.length());
+                } else {
+                    buffer.append('Z');
+                }
+                modified = buffer;
+            }
+            /*
+             * Now ensure that all numbers have at least two digits.
+             */
+            int indexOfLastDigit = 0;
+            for (int i=modified.length(); --i >= 0;) {
+                char c = modified.charAt(i);
+                final boolean isDigit = (c >= '0' && c <= '9'); // Do not use Character.isDigit(char).
+                if (indexOfLastDigit == 0) {
+                    // We were not scaning a number. Check if we are now starting doing so.
+                    if (isDigit) {
+                        indexOfLastDigit = i;
+                    }
+                } else {
+                    // We were scaning a number. Check if we found the begining.
+                    if (!isDigit) {
+                        if (indexOfLastDigit - i == 1) {
+                            // Reuse the buffer if it exists, or create a new one otherwise.
+                            final StringBuilder buffer;
+                            if (modified == date) {
+                                modified = buffer = new StringBuilder(date);
+                            } else {
+                                buffer = (StringBuilder) modified;
+                            }
+                            buffer.insert(i+1, '0');
+                        }
+                        indexOfLastDigit = 0;
+                    }
+                }
+            }
+            date = modified.toString();
+        }
+        return date;
+    }
+
+    /**
      * A string representation of this dimension for debugging purpose only.
      */
     @Debug

Modified: sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/ChannelDecoder.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/ChannelDecoder.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/ChannelDecoder.java [UTF-8] (original)
+++ sis/branches/JDK7/storage/sis-netcdf/src/main/java/org/apache/sis/internal/netcdf/impl/ChannelDecoder.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -107,12 +107,6 @@ public final class ChannelDecoder extend
      */
     private static final Pattern TIME_UNIT_PATTERN = Pattern.compile("(?i)\\bsince\\b");
 
-    /**
-     * {@code true} if the default timezone is UTC, or {@code false} if it shall be the
-     * {@linkplain java.util.TimeZone#getDefault() system default}.
-     */
-    private static final boolean DEFAULT_TIMEZONE_IS_UTC = true;
-
     /*
      * NOTE: the names of the static constants below this point match the names used in the Backus-Naur Form (BNF)
      *       definitions in the NetCDF Classic and 64-bit Offset Format (1.0) specification (link in class javdoc),
@@ -505,7 +499,7 @@ public final class ChannelDecoder extend
                 final int na  = (int) tn;
                 ensureNonNegative(na, tag);
                 switch (tag) {
-                    // More cases may be added later if it appears to exist.
+                    // More cases may be added later if they appear to exist.
                     case ATTRIBUTE: attributes = readAttributes(na); break;
                     default:        throw malformedHeader();
                 }
@@ -553,6 +547,8 @@ public final class ChannelDecoder extend
      * <p>Current implementation does nothing, since the NetCDF binary files that {@code ChannelDecoder}
      * can read do not have groups anyway. Future SIS implementations may honor the given group names if
      * groups support is added.</p>
+     *
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public void setSearchPath(final String... groupNames) throws IOException {
@@ -562,6 +558,9 @@ public final class ChannelDecoder extend
      * Returns the path which is currently set. The array returned by this method may be only
      * a subset of the array given to {@link #setSearchPath(String[])} since only the name of
      * groups which have been found in the NetCDF file are returned by this method.
+     *
+     * @return {@inheritDoc}
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public String[] getSearchPath() throws IOException {
@@ -592,6 +591,7 @@ public final class ChannelDecoder extend
      *
      * @param  name The name of the attribute to search, or {@code null}.
      * @return The attribute value, or {@code null} if none or empty or if the given name was null.
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public String stringValue(final String name) throws IOException {
@@ -605,6 +605,9 @@ public final class ChannelDecoder extend
     /**
      * Returns the value of the attribute of the given name as a number, or {@code null} if none.
      * If there is more than one numeric value, only the first one is returned.
+     *
+     * @return {@inheritDoc}
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public Number numericValue(final String name) throws IOException {
@@ -621,13 +624,16 @@ public final class ChannelDecoder extend
     /**
      * Returns the value of the attribute of the given name as a date, or {@code null} if none.
      * If there is more than one numeric value, only the first one is returned.
+     *
+     * @return {@inheritDoc}
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public Date dateValue(final String name) throws IOException {
         final Attribute attribute = findAttribute(name);
         if (attribute != null) {
             if (attribute.value instanceof String) try {
-                return JDK8.parseDateTime((String) attribute.value, DEFAULT_TIMEZONE_IS_UTC);
+                return JDK8.parseDateTime(Attribute.dateToISO((String) attribute.value));
             } catch (IllegalArgumentException e) {
                 listeners.warning(null, e);
             }
@@ -641,6 +647,7 @@ public final class ChannelDecoder extend
      *
      * @param  values The values to convert. May contains {@code null} elements.
      * @return The converted values. May contains {@code null} elements.
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public Date[] numberToDate(final String symbol, final Number... values) throws IOException {
@@ -648,7 +655,7 @@ public final class ChannelDecoder extend
         final String[] parts = TIME_UNIT_PATTERN.split(symbol);
         if (parts.length == 2) try {
             final UnitConverter converter = Units.valueOf(parts[0]).getConverterToAny(Units.MILLISECOND);
-            final long epoch = JDK8.parseDateTime(parts[1], DEFAULT_TIMEZONE_IS_UTC).getTime();
+            final long epoch = JDK8.parseDateTime(Attribute.dateToISO(parts[1])).getTime();
             for (int i=0; i<values.length; i++) {
                 final Number value = values[i];
                 if (value != null) {
@@ -664,6 +671,9 @@ public final class ChannelDecoder extend
     /**
      * Returns all variables found in the NetCDF file.
      * This method returns a direct reference to an internal array - do not modify.
+     *
+     * @return {@inheritDoc}
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public Variable[] getVariables() throws IOException {
@@ -673,6 +683,9 @@ public final class ChannelDecoder extend
     /**
      * Returns all grid geometries found in the NetCDF file.
      * This method returns a direct reference to an internal array - do not modify.
+     *
+     * @return {@inheritDoc}
+     * @throws IOException {@inheritDoc}
      */
     @Override
     public GridGeometry[] getGridGeometries() throws IOException {
@@ -742,6 +755,8 @@ nextVar:    for (final VariableInfo vari
     /**
      * Returns a string representation to be inserted in {@link org.apache.sis.storage.netcdf.NetcdfStore#toString()}
      * result. This is for debugging purpose only any may change in any future SIS version.
+     *
+     * @return {@inheritDoc}
      */
     @Debug
     @Override

Modified: sis/branches/JDK7/storage/sis-netcdf/src/test/java/org/apache/sis/test/suite/NetcdfTestSuite.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK7/storage/sis-netcdf/src/test/java/org/apache/sis/test/suite/NetcdfTestSuite.java?rev=1587131&r1=1587130&r2=1587131&view=diff
==============================================================================
--- sis/branches/JDK7/storage/sis-netcdf/src/test/java/org/apache/sis/test/suite/NetcdfTestSuite.java [UTF-8] (original)
+++ sis/branches/JDK7/storage/sis-netcdf/src/test/java/org/apache/sis/test/suite/NetcdfTestSuite.java [UTF-8] Mon Apr 14 03:32:30 2014
@@ -35,6 +35,7 @@ import org.junit.BeforeClass;
     org.apache.sis.internal.netcdf.DecoderTest.class,
     org.apache.sis.internal.netcdf.VariableTest.class,
     org.apache.sis.internal.netcdf.GridGeometryTest.class,
+    org.apache.sis.internal.netcdf.impl.AttributeTest.class,
     org.apache.sis.internal.netcdf.impl.ChannelDecoderTest.class,
     org.apache.sis.internal.netcdf.impl.VariableInfoTest.class,
     org.apache.sis.internal.netcdf.impl.GridGeometryInfoTest.class,