Index: trunk/src/javax/json/EmptyArray.java
===================================================================
--- trunk/src/javax/json/EmptyArray.java	(revision 13231)
+++ trunk/src/javax/json/EmptyArray.java	(revision 13231)
@@ -0,0 +1,136 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+package javax.json;
+
+import java.io.Serializable;
+import java.util.AbstractList;
+import java.util.Collections;
+import java.util.List;
+import java.util.RandomAccess;
+
+/**
+ * Private implementation of immutable {@link JsonArray}.
+ *
+ * @author Lukas Jungmann
+ */
+final class EmptyArray extends AbstractList<JsonValue> implements JsonArray, Serializable, RandomAccess {
+
+    private static final long serialVersionUID = 7295439472061642859L;
+
+    @Override
+    public JsonValue get(int index) {
+        throw new IndexOutOfBoundsException("Index: " + index);
+    }
+
+    @Override
+    public int size() {
+        return 0;
+    }
+
+    @Override
+    public JsonObject getJsonObject(int index) {
+        return (JsonObject) get(index);
+    }
+
+    @Override
+    public JsonArray getJsonArray(int index) {
+        return (JsonArray) get(index);
+    }
+
+    @Override
+    public JsonNumber getJsonNumber(int index) {
+        return (JsonNumber) get(index);
+    }
+
+    @Override
+    public JsonString getJsonString(int index) {
+        return (JsonString) get(index);
+    }
+
+    @Override
+    public <T extends JsonValue> List<T> getValuesAs(Class<T> clazz) {
+        return Collections.emptyList();
+    }
+
+    @Override
+    public String getString(int index) {
+        return getJsonString(index).getString();
+    }
+
+    @Override
+    public String getString(int index, String defaultValue) {
+        return defaultValue;
+    }
+
+    @Override
+    public int getInt(int index) {
+        return getJsonNumber(index).intValue();
+    }
+
+    @Override
+    public int getInt(int index, int defaultValue) {
+        return defaultValue;
+    }
+
+    @Override
+    public boolean getBoolean(int index) {
+        return get(index) == JsonValue.TRUE;
+    }
+
+    @Override
+    public boolean getBoolean(int index, boolean defaultValue) {
+        return defaultValue;
+    }
+
+    @Override
+    public boolean isNull(int index) {
+        return get(index) == JsonValue.NULL;
+    }
+
+    @Override
+    public ValueType getValueType() {
+        return ValueType.ARRAY;
+    }
+
+    // Preserves singleton property
+    private Object readResolve() {
+        return JsonValue.EMPTY_JSON_ARRAY;
+    }
+}
Index: trunk/src/javax/json/EmptyObject.java
===================================================================
--- trunk/src/javax/json/EmptyObject.java	(revision 13231)
+++ trunk/src/javax/json/EmptyObject.java	(revision 13231)
@@ -0,0 +1,126 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json;
+
+import java.io.Serializable;
+import java.util.AbstractMap;
+import java.util.Collections;
+import java.util.Set;
+
+/**
+ * Private implementation of immutable {@link JsonObject}.
+ *
+ * @author Lukas Jungmann
+ */
+final class EmptyObject extends AbstractMap<String, JsonValue> implements JsonObject, Serializable {
+
+    private static final long serialVersionUID = -1461653546889072583L;
+
+    @Override
+    public Set<Entry<String, JsonValue>> entrySet() {
+        return Collections.<Entry<String, JsonValue>>emptySet();
+    }
+
+    @Override
+    public JsonArray getJsonArray(String name) {
+        return (JsonArray) get(name);
+    }
+
+    @Override
+    public JsonObject getJsonObject(String name) {
+        return (JsonObject) get(name);
+    }
+
+    @Override
+    public JsonNumber getJsonNumber(String name) {
+        return (JsonNumber) get(name);
+    }
+
+    @Override
+    public JsonString getJsonString(String name) {
+        return (JsonString) get(name);
+    }
+
+    @Override
+    public String getString(String name) {
+        return getJsonString(name).getString();
+    }
+
+    @Override
+    public String getString(String name, String defaultValue) {
+        return defaultValue;
+    }
+
+    @Override
+    public int getInt(String name) {
+        return getJsonNumber(name).intValue();
+    }
+
+    @Override
+    public int getInt(String name, int defaultValue) {
+        return defaultValue;
+    }
+
+    @Override
+    public boolean getBoolean(String name) {
+        throw new NullPointerException();
+    }
+
+    @Override
+    public boolean getBoolean(String name, boolean defaultValue) {
+        return defaultValue;
+    }
+
+    @Override
+    public boolean isNull(String name) {
+        throw new NullPointerException();
+    }
+
+    @Override
+    public ValueType getValueType() {
+        return ValueType.OBJECT;
+    }
+
+    // Preserves singleton property
+    private Object readResolve() {
+        return JsonValue.EMPTY_JSON_OBJECT;
+    }
+}
Index: trunk/src/javax/json/Json.java
===================================================================
--- trunk/src/javax/json/Json.java	(revision 13230)
+++ trunk/src/javax/json/Json.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -41,4 +41,13 @@
 package javax.json;
 
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.io.Reader;
+import java.io.Writer;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.util.Collection;
+import java.util.Map;
+import java.util.Optional;
 import javax.json.spi.JsonProvider;
 import javax.json.stream.JsonGenerator;
@@ -46,6 +55,4 @@
 import javax.json.stream.JsonParser;
 import javax.json.stream.JsonParserFactory;
-import java.io.*;
-import java.util.Map;
 
 /**
@@ -73,8 +80,6 @@
  * All the methods in this class are safe for use by multiple concurrent
  * threads.
- *
- * @author Jitendra Kotamraju
  */
-public class Json {
+public final class Json {
 
     private Json() {
@@ -93,6 +98,6 @@
     /**
      * Creates a JSON parser from a byte stream.
-     * The character encoding of the stream is determined as specified in 
-     * <a href="http://tools.ietf.org/rfc/rfc4627.txt">RFC 4627</a>.
+     * The character encoding of the stream is determined as specified in
+     * <a href="http://tools.ietf.org/rfc/rfc7159.txt">RFC 7159</a>.
      *
      * @param in i/o stream from which JSON is to be read
@@ -212,5 +217,5 @@
      * Creates a JSON reader from a byte stream. The character encoding of
      * the stream is determined as described in
-     * <a href="http://tools.ietf.org/rfc/rfc4627.txt">RFC 4627</a>.
+     * <a href="http://tools.ietf.org/rfc/rfc7159.txt">RFC 7159</a>.
      *
      * @param in a byte stream from which JSON is to be read
@@ -259,4 +264,32 @@
 
     /**
+     * Creates a JSON array builder, initialized with the specified array
+     *
+     * @param array the initial array in the builder
+     * @return a JSON array builder
+     *
+     * @since 1.1
+     */
+    public static JsonArrayBuilder createArrayBuilder(JsonArray array) {
+        return JsonProvider.provider().createArrayBuilder(array);
+    }
+
+    /**
+     * Creates a JSON array builder, initialized with the content of specified {@code collection}.
+     * If the @{code collection} contains {@link Optional}s then resulting JSON array builder
+     * contains the value from the {@code collection} only if the {@link Optional} is not empty.
+     *
+     * @param collection the initial data for the builder
+     * @return a JSON array builder
+     * @exception IllegalArgumentException if the value from the {@code collection} cannot be converted
+     *            to the corresponding {@link JsonValue}
+     *
+     * @since 1.1
+     */
+    public static JsonArrayBuilder createArrayBuilder(Collection<?> collection) {
+        return JsonProvider.provider().createArrayBuilder(collection);
+    }
+
+    /**
      * Creates a JSON object builder
      *
@@ -265,4 +298,132 @@
     public static JsonObjectBuilder createObjectBuilder() {
         return JsonProvider.provider().createObjectBuilder();
+    }
+
+    /**
+     * Creates a JSON object builder, initialized with the specified object.
+     *
+     * @param object the initial object in the builder
+     * @return a JSON object builder
+     *
+     * @since 1.1
+     */
+    public static JsonObjectBuilder createObjectBuilder(JsonObject object) {
+        return JsonProvider.provider().createObjectBuilder(object);
+    }
+
+    /**
+     * Creates a JSON object builder, initialized with the data from specified {@code map}.
+     * If the @{code map} contains {@link Optional}s then resulting JSON object builder
+     * contains the key from the {@code map} only if the {@link Optional} is not empty.
+     *
+     * @param map the initial object in the builder
+     * @return a JSON object builder
+     * @exception IllegalArgumentException if the value from the {@code map} cannot be converted
+     *            to the corresponding {@link JsonValue}
+     *
+     * @since 1.1
+     */
+    public static JsonObjectBuilder createObjectBuilder(Map<String, Object> map) {
+        return JsonProvider.provider().createObjectBuilder(map);
+    }
+
+    /**
+     * Creates JSON Pointer (<a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>)
+     * from given {@code jsonPointer} string.
+     * <ul>
+     *     <li>An empty {@code jsonPointer} string defines a reference to the target itself.</li>
+     *     <li>If the {@code jsonPointer} string is non-empty, it must be a sequence of '{@code /}' prefixed tokens.</li>
+     * </ul>
+     *
+     * @param jsonPointer the valid escaped JSON Pointer string
+     * @throws NullPointerException if {@code jsonPointer} is {@code null}
+     * @throws JsonException if {@code jsonPointer} is not a valid JSON Pointer
+     * @return a JSON Pointer
+     *
+     * @since 1.1
+     */
+    public static JsonPointer createPointer(String jsonPointer) {
+        return JsonProvider.provider().createPointer(jsonPointer);
+    }
+
+    /**
+     * Creates a JSON Patch builder (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>).
+     *
+     * @return a JSON Patch builder
+     *
+     * @since 1.1
+     */
+    public static JsonPatchBuilder createPatchBuilder() {
+        return JsonProvider.provider().createPatchBuilder();
+    }
+
+    /**
+     * Creates a JSON Patch builder
+     * (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>),
+     * initialized with the specified operations.
+     *
+     * @param array the initial patch operations
+     * @return a JSON Patch builder
+     *
+     * @since 1.1
+     */
+    public static JsonPatchBuilder createPatchBuilder(JsonArray array) {
+        return JsonProvider.provider().createPatchBuilder(array);
+    }
+
+    /**
+     * Creates a JSON Patch (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>)
+     * from the specified operations.
+     *
+     * @param array patch operations
+     * @return a JSON Patch
+     *
+     * @since 1.1
+     */
+    public static JsonPatch createPatch(JsonArray array) {
+        return JsonProvider.provider().createPatch(array);
+    }
+
+    /**
+     * Generates a JSON Patch (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>)
+     * from the source and target {@code JsonStructure}.
+     * The generated JSON Patch need not be unique.
+     *
+     * @param source the source
+     * @param target the target, must be the same type as the source
+     * @return a JSON Patch which when applied to the source, yields the target
+     *
+     * @since 1.1
+     */
+    public static JsonPatch createDiff(JsonStructure source, JsonStructure target) {
+        return JsonProvider.provider().createDiff(source, target);
+    }
+
+    /**
+     * Creates JSON Merge Patch (<a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>)
+     * from specified {@code JsonValue}.
+     *
+     * @param patch the patch
+     * @return a JSON Merge Patch
+     *
+     * @since 1.1
+     */
+    public static JsonMergePatch createMergePatch(JsonValue patch) {
+        return JsonProvider.provider().createMergePatch(patch);
+    }
+
+    /**
+     * Generates a JSON Merge Patch (<a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>)
+     * from the source and target {@code JsonValue}s
+     * which when applied to the {@code source}, yields the {@code target}.
+     *
+     * @param source the source
+     * @param target the target
+     * @return a JSON Merge Patch
+     *
+     * @since 1.1
+     */
+    public static JsonMergePatch createMergeDiff(JsonValue source, JsonValue target) {
+        return JsonProvider.provider().createMergeDiff(source, target);
     }
 
@@ -283,3 +444,101 @@
     }
 
+    /**
+     * Creates a JsonString.
+     *
+     * @param value a JSON string
+     * @return the JsonString for the string
+     *
+     * @since 1.1
+     */
+    public static JsonString createValue(String value) {
+        return JsonProvider.provider().createValue(value);
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public static JsonNumber createValue(int value) {
+        return JsonProvider.provider().createValue(value);
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public static JsonNumber createValue(long value) {
+        return JsonProvider.provider().createValue(value);
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public static JsonNumber createValue(double value) {
+        return JsonProvider.provider().createValue(value);
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public static JsonNumber createValue(BigDecimal value) {
+        return JsonProvider.provider().createValue(value);
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public static JsonNumber createValue(BigInteger value) {
+        return JsonProvider.provider().createValue(value);
+    }
+
+    /**
+     * Encodes (escapes) a passed string as defined by <a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>.
+     * This method doesn't validate the passed JSON-pointer string.
+     *
+     * @param pointer the JSON-pointer string to encode
+     * @return encoded JSON-pointer string
+     * 
+     * @since 1.1
+     */
+    public static String encodePointer(String pointer) {
+        return pointer.replace("~", "~0").replace("/", "~1");
+    }
+
+    /**
+     * Decodes a passed JSON-pointer string as defined by <a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>.
+     * This method doesn't validate the passed JSON-pointer string.
+     *
+     * @param escaped the JSON-pointer string to decode
+     * @return decoded JSON-pointer string
+     *     
+     * @since 1.1
+     */
+    public static String decodePointer(String escaped) {
+        return escaped.replace("~1", "/").replace("~0", "~");
+    }
+
 }
Index: trunk/src/javax/json/JsonArray.java
===================================================================
--- trunk/src/javax/json/JsonArray.java	(revision 13230)
+++ trunk/src/javax/json/JsonArray.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -42,4 +42,7 @@
 
 import java.util.List;
+import java.util.function.Function;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
 
 /**
@@ -111,6 +114,4 @@
  * whether directly or using its collection views, results in an 
  * {@code UnsupportedOperationException}.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonArray extends JsonStructure, List<JsonValue> {
@@ -165,5 +166,5 @@
 
     /**
-     * Returns a list a view of the specified type for the array. This method
+     * Returns a list view of the specified type for the array. This method
      * does not verify if there is a value of wrong type in the array. Providing
      * this typesafe view dynamically may cause a program fail with a
@@ -172,8 +173,35 @@
      * method returns.
      *
+     * @param <T> The type of the List for the array
      * @param clazz a JsonValue type
-     * @return a list view of the  specified type
+     * @return a list view of the specified type
      */
     <T extends JsonValue> List<T> getValuesAs(Class<T> clazz);
+
+    /**
+     * Returns a list view for the array. The value and the type of the elements
+     * in the list is specified by the {@code func} argument.
+     * <p>This method can be used to obtain a list of the unwrapped types, such as
+     * <pre>{@code
+     *     List<String> strings = ary1.getValuesAs(JsonString::getString);
+     *     List<Integer> ints = ary2.getValuesAs(JsonNumber::intValue);
+     * } </pre>
+     * or a list of simple projections, such as
+     * <pre> {@code
+     *     List<Integer> stringsizes = ary1.getValueAs((JsonString v)->v.getString().length();
+     * } </pre>
+     * @param <K> The element type (must be a subtype of JsonValue) of this JsonArray.
+     * @param <T> The element type of the returned List
+     * @param func The function that maps the elements of this JsonArray to the target elements.
+     * @return A List of the specified values and type.
+     * @throws ClassCastException if the {@code JsonArray} contains a value of wrong type
+     *
+     * @since 1.1
+     */
+    default <T, K extends JsonValue> List<T> getValuesAs(Function<K, T> func) {
+        @SuppressWarnings("unchecked")
+        Stream<K> stream = (Stream<K>) stream();
+        return stream.map(func).collect(Collectors.toList());
+    }
 
     /**
@@ -195,5 +223,7 @@
      * the specified default value is returned.
      *
-     * @param index index of the JsonString value
+     * @param index index of the {@code JsonString} value
+     * @param defaultValue the String to return if the {@code JsonValue} at the
+     *    specified position is not a {@code JsonString}
      * @return the String value at the specified position in this array,
      * or the specified default value
@@ -220,4 +250,6 @@
      *
      * @param index index of the {@code JsonNumber} value
+     * @param defaultValue the int value to return if the {@code JsonValue} at
+     *     the specified position is not a {@code JsonNumber}
      * @return the int value at the specified position in this array,
      * or the specified default value
@@ -247,4 +279,6 @@
      *
      * @param index index of the JSON boolean value
+     * @param defaultValue the boolean value to return if the {@code JsonValue}
+     *    at the specified position is neither TRUE nor FALSE
      * @return the boolean value at the specified position,
      * or the specified default value
@@ -258,8 +292,7 @@
      * @param index index of the JSON null value
      * @return return true if the value at the specified location is
-     * {@code JsonValue.NUL}, otherwise false
+     * {@code JsonValue.NULL}, otherwise false
      * @throws IndexOutOfBoundsException if the index is out of range
      */
     boolean isNull(int index);
-
 }
Index: trunk/src/javax/json/JsonArrayBuilder.java
===================================================================
--- trunk/src/javax/json/JsonArrayBuilder.java	(revision 13230)
+++ trunk/src/javax/json/JsonArrayBuilder.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -45,8 +45,11 @@
 
 /**
- * A builder for creating {@link JsonArray} models from scratch. This
- * interface initializes an empty JSON array model and provides methods to add
- * values to the array model and to return the resulting array. The methods
- * in this class can be chained to add multiple values to the array.
+ * A builder for creating {@link JsonArray} models from scratch, and for
+ * modifying a existing {@code JsonArray}.
+ * <p>A {@code JsonArrayBuilder} can start with an empty or a non-empty
+ * JSON array model. This interface provides methods to add, insert, remove
+ * and replace values in the JSON array model.</p>
+ * <p>Methods in this class can be chained to perform multiple values to
+ * the array.</p>
  *
  * <p>The class {@link javax.json.Json} contains methods to create the builder
@@ -64,5 +67,4 @@
  * way to create multiple instances.
  *
- * <a id="JsonArrayBuilderExample1"/>
  * The example code below shows how to build a {@code JsonArray} object
  * that represents the following JSON array:
@@ -165,5 +167,5 @@
      * @param value the number value
      * @return this array builder
-     * @throws NumberFormatException if the value is Not-a-Number(NaN) or 
+     * @throws NumberFormatException if the value is Not-a-Number (NaN) or
      *      infinity
      *
@@ -207,4 +209,432 @@
 
     /**
+     * Adds all elements of the array in the specified array builder to the array.
+     *
+     * @param builder the array builder
+     * @return this array builder
+     * @throws NullPointerException if the specified builder is null
+     *
+     @since 1.1
+     */
+    default JsonArrayBuilder addAll(JsonArrayBuilder builder) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Inserts a value to the array at the specified position. Shifts the value
+     * currently at that position (if any) and any subsequent values to the right
+     * (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the JSON value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, JsonValue value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a value to the array as a {@link JsonString} at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the string value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, String value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a value to the array as a {@link JsonNumber} at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, BigDecimal value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a value to the array as a {@link JsonNumber} at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, BigInteger value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a value to the array as a {@link JsonNumber} at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, int value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a value to the array as a {@link JsonNumber} at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, long value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a value to the array as a {@link JsonNumber} at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws NumberFormatException if the value is Not-a-Number (NaN) or
+     *      infinity
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, double value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a {@link JsonValue#TRUE}  or {@link JsonValue#FALSE} value to the
+     * array at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param value the boolean value
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, boolean value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a {@link JsonValue#NULL} value to the array at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder addNull(int index) {
+        return add(index, JsonValue.NULL);
+    }
+
+    /**
+     * Adds a {@link JsonObject} from an object builder to the array at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param builder the object builder
+     * @return this array builder
+     * @throws NullPointerException if the specified builder is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, JsonObjectBuilder builder) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Adds a {@link JsonArray} from an array builder to the array at the specified position.
+     * Shifts the value currently at that position (if any) and any subsequent values
+     * to the right (adds one to their indices).  Index starts with 0.
+     *
+     * @param index the position in the array
+     * @param builder the array builder
+     * @return this array builder
+     * @throws NullPointerException if the specified builder is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index > array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder add(int index, JsonArrayBuilder builder) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value at the
+     * specified position.
+     *
+     * @param index the position in the array
+     * @param value the JSON value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, JsonValue value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonString} at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the string value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, String value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonNumber} at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, BigDecimal value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonNumber} at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws NullPointerException if the specified value is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, BigInteger value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonNumber} at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, int value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonNumber} at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, long value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonNumber} at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the number value
+     * @return this array builder
+     * @throws NumberFormatException if the value is Not-a-Number (NaN) or
+     *      infinity
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @see JsonNumber
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, double value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with
+     * a {@link JsonValue#TRUE}  or {@link JsonValue#FALSE} value
+     * at the specified position.
+     *
+     * @param index the position in the array
+     * @param value the boolean value
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, boolean value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with
+     * a {@link JsonValue#NULL} value at the specified position.
+     *
+     * @param index the position in the array
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder setNull(int index) {
+        return set(index, JsonValue.NULL);
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonObject} from an object builder at the specified position.
+     *
+     * @param index the position in the array
+     * @param builder the object builder
+     * @return this array builder
+     * @throws NullPointerException if the specified builder is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, JsonObjectBuilder builder) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Replaces a value in the array with the specified value as a
+     * {@link JsonArray} from an array builder at the specified position.
+     *
+     * @param index the position in the array
+     * @param builder the array builder
+     * @return this array builder
+     * @throws NullPointerException if the specified builder is null
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder set(int index, JsonArrayBuilder builder) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Remove the value in the array at the specified position.
+     * Shift any subsequent values to the left (subtracts one from their
+     * indices.
+     *
+     * @param index the position in the array
+     * @return this array builder
+     * @throws IndexOutOfBoundsException if the index is out of range
+     *   {@code (index < 0 || index >= array size)}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder remove(int index) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
      * Returns the current array.
      *
Index: trunk/src/javax/json/JsonBuilderFactory.java
===================================================================
--- trunk/src/javax/json/JsonBuilderFactory.java	(revision 13230)
+++ trunk/src/javax/json/JsonBuilderFactory.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -41,4 +41,5 @@
 package javax.json;
 
+import java.util.Collection;
 import java.util.Map;
 
@@ -71,6 +72,4 @@
  * <p> All the methods in this class are safe for use by multiple concurrent
  * threads.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonBuilderFactory {
@@ -85,4 +84,30 @@
 
     /**
+     * Creates a {@code JsonObjectBuilder} instance, initialized with an object.
+     *
+     * @param object the initial object in the builder
+     * @return a JSON object builder
+     * @throws NullPointerException if specified object is {@code null}
+     *
+     * @since 1.1
+     */
+    default JsonObjectBuilder createObjectBuilder(JsonObject object) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a {@code JsonObjectBuilder} instance, initialized with the specified object.
+     *
+     * @param object the initial object in the builder
+     * @return a JSON object builder
+     * @throws NullPointerException if specified object is {@code null}
+     *
+     * @since 1.1
+     */
+    default JsonObjectBuilder createObjectBuilder(Map<String, Object> object) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
      * Creates a {@code JsonArrayBuilder} instance that is used to build
      * {@link JsonArray}
@@ -91,4 +116,31 @@
      */
     JsonArrayBuilder createArrayBuilder();
+
+    /**
+     * Creates a {@code JsonArrayBuilder} instance, initialized with an array.
+     *
+     * @param array the initial array in the builder
+     * @return a JSON array builder
+     * @throws NullPointerException if specified array is {@code null}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder createArrayBuilder(JsonArray array) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a {@code JsonArrayBuilder} instance,
+     * initialized with the content of specified collection.
+     *
+     * @param collection the initial data for the builder
+     * @return a JSON array builder
+     * @throws NullPointerException if specified collection is {@code null}
+     *
+     * @since 1.1
+     */
+    default JsonArrayBuilder createArrayBuilder(Collection<?> collection) {
+        throw new UnsupportedOperationException();
+    }
 
     /**
Index: trunk/src/javax/json/JsonException.java
===================================================================
--- trunk/src/javax/json/JsonException.java	(revision 13230)
+++ trunk/src/javax/json/JsonException.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -44,6 +44,4 @@
  * <code>JsonException</code> indicates that some exception happened during
  * JSON processing.
- *
- * @author Jitendra Kotamraju
  */
 public class JsonException extends RuntimeException {
Index: trunk/src/javax/json/JsonMergePatch.java
===================================================================
--- trunk/src/javax/json/JsonMergePatch.java	(revision 13231)
+++ trunk/src/javax/json/JsonMergePatch.java	(revision 13231)
@@ -0,0 +1,87 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json;
+
+/**
+ * <p>This interface represents an implementation of a JSON Merge Patch
+ * as defined by <a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>.
+ * </p>
+ * <p>A {@code JsonMergePatch} can be instantiated with {@link Json#createMergePatch(JsonValue)}
+ * by specifying the patch operations in a JSON Merge Patch or using {@link Json#createMergeDiff(JsonValue, JsonValue)}
+ * to create a JSON Merge Patch based on the difference between two {@code JsonValue}s.
+ * </p>
+ * The following illustrates both approaches.
+ * <p>1. Construct a JsonMergePatch with an existing JSON Merge Patch.
+ * <pre>{@code
+ *   JsonValue contacts = ... ; // The target to be patched
+ *   JsonValue patch = ...  ; // JSON Merge Patch
+ *   JsonMergePatch mergePatch = Json.createMergePatch(patch);
+ *   JsonValue result = mergePatch.apply(contacts);
+ * } </pre>
+ * 2. Construct a JsonMergePatch from a difference between two {@code JsonValue}s.
+ * <pre>{@code
+ *   JsonValue source = ... ; // The source object
+ *   JsonValue target = ... ; // The modified object
+ *   JsonMergePatch mergePatch = Json.createMergeDiff(source, target); // The diff between source and target in a Json Merge Patch format
+ * } </pre>
+ *
+ * @see <a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>
+ *
+ * @since 1.1
+ */
+public interface JsonMergePatch {
+
+    /**
+     * Applies the JSON Merge Patch to the specified {@code target}.
+     * The target is not modified by the patch.
+     *
+     * @param target the target to apply the merge patch
+     * @return the transformed target after the patch
+     */
+    JsonValue apply(JsonValue target);
+
+    /**
+     * Returns the {@code JsonMergePatch} as {@code JsonValue}.
+     *
+     * @return this {@code JsonMergePatch} as {@code JsonValue}
+     */
+    JsonValue toJsonValue();
+}
Index: trunk/src/javax/json/JsonNumber.java
===================================================================
--- trunk/src/javax/json/JsonNumber.java	(revision 13230)
+++ trunk/src/javax/json/JsonNumber.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -51,13 +51,11 @@
  * value internally.
  * The {@code BigDecimal} object can be constructed from the following types:
- * {@link BigDecimal#BigDecimal(int) <code>int</code>},
- * {@link BigDecimal#BigDecimal(long) <code>long</code>},
- * {@link BigDecimal#BigDecimal(BigInteger) <code>BigInteger</code>},
- * {@link BigDecimal#valueOf(double) <code>double</code>}, and
- * {@link BigDecimal#BigDecimal(String) <code>String</code>}.
+ * <code>int</code> {@link BigDecimal#BigDecimal(int)},
+ * <code>long</code> {@link BigDecimal#BigDecimal(long)},
+ * <code>BigInteger</code> {@link BigDecimal#BigDecimal(BigInteger)},
+ * <code>double</code> {@link BigDecimal#valueOf(double)}, and
+ * <code>String</code> {@link BigDecimal#BigDecimal(String)}.
  * Some of the method semantics in this class are defined using the
  * {@code BigDecimal} semantics.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonNumber extends JsonValue {
@@ -138,5 +136,5 @@
 
     /**
-     * Returns this JSON number as a {@link BigDecimal} object. This is a
+     * Returns this JSON number as a {@link BigInteger} object. This is a
      * convenience method for {@code bigDecimalValue().toBigIntegerExact()}.
      *
@@ -167,4 +165,15 @@
 
     /**
+     * Returns this JSON number as a {@link Number} object.
+     *
+     * @return a {@link Number} representation of the JSON number
+     *
+     * @since 1.1
+     */
+    default Number numberValue() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
      * Returns a JSON text representation of the JSON number. The
      * representation is equivalent to {@link BigDecimal#toString()}.
@@ -181,7 +190,7 @@
      * objects are <i>equal</i>
      *
-     * @param obj the object to be compared for equality with 
+     * @param obj the object to be compared for equality with
      *      this {@code JsonNumber}
-     * @return {@code true} if the specified object is equal to this 
+     * @return {@code true} if the specified object is equal to this
      *      {@code JsonNumber}
      */
Index: trunk/src/javax/json/JsonObject.java
===================================================================
--- trunk/src/javax/json/JsonObject.java	(revision 13230)
+++ trunk/src/javax/json/JsonObject.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -125,6 +125,4 @@
  * name/value pairs are added to the corresponding builder or the order
  * in which name/value pairs appear in the corresponding stream.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonObject extends JsonStructure, Map<String, JsonValue> {
@@ -266,5 +264,5 @@
      *
      * @param name name whose associated value is checked
-     * @return return true if the associated value is {@code JsonValue.NUL},
+     * @return return true if the associated value is {@code JsonValue.NULL},
      * otherwise false
      * @throws NullPointerException if the specified name doesn't have any
Index: trunk/src/javax/json/JsonObjectBuilder.java
===================================================================
--- trunk/src/javax/json/JsonObjectBuilder.java	(revision 13230)
+++ trunk/src/javax/json/JsonObjectBuilder.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -65,5 +65,4 @@
  * way to create multiple instances.
  *
- * <a id="JsonObjectBuilderExample1"/>
  * The example code below shows how to build a {@code JsonObject} model that
  * represents the following JSON object:
@@ -207,5 +206,5 @@
      * @param value value in the name/value pair
      * @return this object builder
-     * @throws NumberFormatException if the value is Not-a-Number(NaN) or 
+     * @throws NumberFormatException if the value is Not-a-Number (NaN) or 
      * infinity
      * @throws NullPointerException if the specified name is null
@@ -269,4 +268,32 @@
 
     /**
+     * Adds all name/value pairs in the JSON object associated with the specified
+     * object builder to the JSON object associated with this object builder.
+     * The newly added name/value pair will replace any existing name/value pair with
+     * the same name.
+     *
+     * @param builder the specified object builder
+     * @return this object builder
+     * @throws NullPointerException if the specified builder is null
+     * @since 1.1
+     */
+    default JsonObjectBuilder addAll(JsonObjectBuilder builder) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Remove the name/value pair from the JSON object associated with this
+     * object builder if it is present.
+     *
+     * @param name the name in the name/value pair to be removed
+     * @return this object builder
+     * @throws NullPointerException if the specified name is null
+     * @since 1.1
+     */
+    default JsonObjectBuilder remove(String name) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
      * Returns the JSON object associated with this object builder. 
      * The iteration order for the {@code JsonObject} is based
Index: trunk/src/javax/json/JsonPatch.java
===================================================================
--- trunk/src/javax/json/JsonPatch.java	(revision 13231)
+++ trunk/src/javax/json/JsonPatch.java	(revision 13231)
@@ -0,0 +1,163 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json;
+
+/**
+ * <p>This interface represents an immutable implementation of a JSON Patch
+ * as defined by <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>.
+ * </p>
+ * <p>A {@code JsonPatch} can be instantiated with {@link Json#createPatch(JsonArray)}
+ * by specifying the patch operations in a JSON Patch. Alternately, it
+ * can also be constructed with a {@link JsonPatchBuilder}.
+ * </p>
+ * The following illustrates both approaches.
+ * <p>1. Construct a JsonPatch with a JSON Patch.
+ * <pre>{@code
+ *   JsonArray contacts = ... // The target to be patched
+ *   JsonArray patch = ...  ; // JSON Patch
+ *   JsonPatch jsonpatch = Json.createPatch(patch);
+ *   JsonArray result = jsonpatch.apply(contacts);
+ * } </pre>
+ * 2. Construct a JsonPatch with JsonPatchBuilder.
+ * <pre>{@code
+ *   JsonPatchBuilder builder = Json.createPatchBuilder();
+ *   JsonArray result = builder.add("/John/phones/office", "1234-567")
+ *                             .remove("/Amy/age")
+ *                             .build()
+ *                             .apply(contacts);
+ * } </pre>
+ *
+ * @see <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>
+ *
+ * @since 1.1
+ */
+public interface JsonPatch {
+
+    /**
+     * This enum represents the list of valid JSON Patch operations
+     * as defined by <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>.
+     *
+     * @see <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>
+     */
+    enum Operation {
+
+        /**
+         * "add" operation.
+         */
+        ADD("add"),
+
+        /**
+         * "remove" operation.
+         */
+        REMOVE("remove"),
+
+        /**
+         * "remove" operation.
+         */
+        REPLACE("replace"),
+
+        /**
+         * "move" operation.
+         */
+        MOVE("move"),
+
+        /**
+         * "copy" operation.
+         */
+        COPY("copy"),
+
+        /**
+         * "test" operation.
+         */
+        TEST("test");
+
+        private final String operationName;
+
+        private Operation(String operationName) {
+            this.operationName = operationName;
+        }
+
+        /**
+         * Returns enum constant name as lower case string.
+         *
+         * @return lower case name of the enum constant
+         */
+        public String operationName() {
+            return operationName;
+        }
+
+        /**
+         * Returns the enum constant with the specified name.
+         *
+         * @param operationName {@code operationName} to convert to the enum constant.
+         * @return the enum constant for given {@code operationName}
+         * @throws JsonException if given {@code operationName} is not recognized
+         */
+        public static Operation fromOperationName(String operationName) {
+            for (Operation op : values()) {
+                if (op.operationName().equalsIgnoreCase(operationName)) {
+                    return op;
+                }
+            }
+            throw new JsonException("Illegal value for the operationName of the JSON patch operation: " + operationName);
+        }
+    }
+
+    /**
+     * Applies the patch operations to the specified {@code target}.
+     * The target is not modified by the patch.
+     *
+     * @param <T> the target type, must be a subtype of {@link JsonStructure}
+     * @param target the target to apply the patch operations
+     * @return the transformed target after the patch
+     * @throws JsonException if the supplied JSON Patch is malformed or if
+     *    it contains references to non-existing members
+     */
+    <T extends JsonStructure> T apply(T target);
+
+    /**
+     * Returns the {@code JsonPatch} as {@code JsonArray}.
+     *
+     * @return this {@code JsonPatch} as {@code JsonArray}
+     */
+    JsonArray toJsonArray();
+
+}
Index: trunk/src/javax/json/JsonPatchBuilder.java
===================================================================
--- trunk/src/javax/json/JsonPatchBuilder.java	(revision 13231)
+++ trunk/src/javax/json/JsonPatchBuilder.java	(revision 13231)
@@ -0,0 +1,210 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json;
+
+/**
+ * A builder for constructing a JSON Patch as defined by
+ * <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a> by adding
+ * JSON Patch operations incrementally.
+ * <p>
+ * The following illustrates the approach.
+ * <pre>
+ *   JsonPatchBuilder builder = Json.createPatchBuilder();
+ *   JsonPatch patch = builder.add("/John/phones/office", "1234-567")
+ *                            .remove("/Amy/age")
+ *                            .build();
+ * </pre>
+ * The result is equivalent to the following JSON Patch.
+ * <pre>
+ * [
+ *    {"op" = "add", "path" = "/John/phones/office", "value" = "1234-567"},
+ *    {"op" = "remove", "path" = "/Amy/age"}
+ * ] </pre>
+ *
+ * @see <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>
+ *
+ * @since 1.1
+ */
+public interface JsonPatchBuilder {
+
+    /**
+     * Adds an "add" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder add(String path, JsonValue value);
+
+    /**
+     * Adds an "add" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder add(String path, String value);
+
+    /**
+     * Adds an "add" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder add(String path, int value);
+
+    /**
+     * Adds an "add" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder add(String path, boolean value);
+
+    /**
+     * Adds a "remove" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer.
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder remove(String path);
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder replace(String path, JsonValue value);
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder replace(String path, String value);
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder replace(String path, int value);
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder replace(String path, boolean value);
+
+    /**
+     * Adds a "move" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param from the "from" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder move(String path, String from);
+
+    /**
+     * Adds a "copy" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param from the "from" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder copy(String path, String from);
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder test(String path, JsonValue value);
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder test(String path, String value);
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder test(String path, int value);
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     *
+     * @param path the "path" member of the operation. Must be a valid escaped JSON-Pointer string.
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    JsonPatchBuilder test(String path, boolean value);
+
+
+    /**
+     * Returns the JSON Patch.
+     *
+     * @return a JSON Patch
+     */
+    JsonPatch build();
+
+}
Index: trunk/src/javax/json/JsonPointer.java
===================================================================
--- trunk/src/javax/json/JsonPointer.java	(revision 13231)
+++ trunk/src/javax/json/JsonPointer.java	(revision 13231)
@@ -0,0 +1,140 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json;
+
+/**
+ * <p>This interface represents an immutable implementation of a JSON Pointer
+ * as defined by <a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>.
+ * </p>
+ * <p> A JSON Pointer, when applied to a target {@link JsonValue},
+ * defines a reference location in the target.</p>
+ * <p> An empty JSON Pointer string defines a reference to the target itself.</p>
+ * <p> If the JSON Pointer string is non-empty, it must be a sequence
+ * of '/' prefixed tokens, and the target must either be a {@link JsonArray}
+ * or {@link JsonObject}. If the target is a {@code JsonArray}, the pointer
+ * defines a reference to an array element, and the last token specifies the index.
+ * If the target is a {@link JsonObject}, the pointer defines a reference to a
+ * name/value pair, and the last token specifies the name.
+ * </p>
+ * <p> The method {@link #getValue getValue()} returns the referenced value.
+ * Methods {@link #add add()}, {@link #replace replace()},
+ * and {@link #remove remove()} execute operations specified in
+ * <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>. </p>
+ *
+ * @see <a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>
+ * @see <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>
+ *
+ * @since 1.1
+ */
+public interface JsonPointer {
+
+    /**
+     * Adds or replaces a value at the referenced location in the specified
+     * {@code target} with the specified {@code value}.
+     * <ol>
+     * <li>If the reference is the target (empty JSON Pointer string),
+     * the specified {@code value}, which must be the same type as
+     * specified {@code target}, is returned.</li>
+     * <li>If the reference is an array element, the specified {@code value} is inserted
+     * into the array, at the referenced index. The value currently at that location, and
+     * any subsequent values, are shifted to the right (adds one to the indices).
+     * Index starts with 0. If the reference is specified with a "-", or if the
+     * index is equal to the size of the array, the value is appended to the array.</li>
+     * <li>If the reference is a name/value pair of a {@code JsonObject}, and the
+     * referenced value exists, the value is replaced by the specified {@code value}.
+     * If the value does not exist, a new name/value pair is added to the object.</li>
+     * </ol>
+     *
+     * @param <T> the target type, must be a subtype of {@link JsonValue}
+     * @param target the target referenced by this {@code JsonPointer}
+     * @param value the value to be added
+     * @return the transformed {@code target} after the value is added.
+     * @throws NullPointerException if {@code target} is {@code null}
+     * @throws JsonException if the reference is an array element and
+     * the index is out of range ({@code index < 0 || index > array size}),
+     * or if the pointer contains references to non-existing objects or arrays.
+     */
+    <T extends JsonStructure> T add(T target, JsonValue value);
+
+    /**
+     * Removes the value at the reference location in the specified {@code target}.
+     *
+     * @param <T> the target type, must be a subtype of {@link JsonValue}
+     * @param target the target referenced by this {@code JsonPointer}
+     * @return the transformed {@code target} after the value is removed.
+     * @throws NullPointerException if {@code target} is {@code null}
+     * @throws JsonException if the referenced value does not exist,
+     *    or if the reference is the target.
+     */
+    <T extends JsonStructure> T remove(T target);
+
+    /**
+     * Replaces the value at the referenced location in the specified
+     * {@code target} with the specified {@code value}.
+     *
+     * @param <T> the target type, must be a subtype of {@link JsonValue}
+     * @param target the target referenced by this {@code JsonPointer}
+     * @param value the value to be stored at the referenced location
+     * @return the transformed {@code target} after the value is replaced.
+     * @throws NullPointerException if {@code target} is {@code null}
+     * @throws JsonException if the referenced value does not exist,
+     *    or if the reference is the target.
+     */
+    <T extends JsonStructure> T replace(T target, JsonValue value);
+
+    /**
+     * Returns {@code true} if there is a value at the referenced location in the specified {@code target}.
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @return {@code true} if this pointer points to a value in a specified {@code target}.
+     */
+    boolean containsValue(JsonStructure target);
+
+    /**
+     * Returns the value at the referenced location in the specified {@code target}.
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @return the referenced value in the target.
+     * @throws NullPointerException if {@code target} is null
+     * @throws JsonException if the referenced value does not exist
+     */
+    JsonValue getValue(JsonStructure target);
+}
Index: trunk/src/javax/json/JsonReader.java
===================================================================
--- trunk/src/javax/json/JsonReader.java	(revision 13230)
+++ trunk/src/javax/json/JsonReader.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -51,5 +51,4 @@
  *
  * <p>
- * <a id="JsonReaderExample1"/>
  * The following example demonstrates how to read an empty JSON array from
  * a string:
@@ -75,6 +74,4 @@
  * </code>
  * </pre>
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonReader extends  /*Auto*/Closeable {
@@ -91,6 +88,6 @@
      * @throws javax.json.stream.JsonParsingException if a JSON object or array
      *     cannot be created due to incorrect representation
-     * @throws IllegalStateException if read, readObject, readArray or
-     *     close method is already called
+     * @throws IllegalStateException if read, readObject, readArray,
+     *     readValue or close method is already called
      */
     JsonStructure read();
@@ -107,6 +104,6 @@
      * @throws javax.json.stream.JsonParsingException if a JSON object cannot
      *     be created due to incorrect representation
-     * @throws IllegalStateException if read, readObject, readArray or
-     *     close method is already called
+     * @throws IllegalStateException if read, readObject, readArray,
+     *     readValue or close method is already called
      */
     JsonObject readObject();
@@ -123,8 +120,28 @@
      * @throws javax.json.stream.JsonParsingException if a JSON array cannot
      *     be created due to incorrect representation
-     * @throws IllegalStateException if read, readObject, readArray or
-     *     close method is already called
+     * @throws IllegalStateException if read, readObject, readArray,
+     *     readValue or close method is already called
      */
     JsonArray readArray();
+
+    /**
+     * Returns a JSON value that is represented in
+     * the input source. This method needs to be called
+     * only once for a reader instance.
+     *
+     * @return a JSON value
+     * @throws JsonException if a JSON value
+     *     be created due to i/o error (IOException would be
+     *     cause of JsonException)
+     * @throws javax.json.stream.JsonParsingException if a JSON value
+     *     cannot be created due to incorrect representation
+     * @throws IllegalStateException if read, readObject, readArray,
+     *     readValue or close method is already called
+     *
+     * @since 1.1
+     */
+    default JsonValue readValue() {
+        throw new UnsupportedOperationException();
+    }
 
     /**
Index: trunk/src/javax/json/JsonReaderFactory.java
===================================================================
--- trunk/src/javax/json/JsonReaderFactory.java	(revision 13230)
+++ trunk/src/javax/json/JsonReaderFactory.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -68,6 +68,4 @@
  * <p> All the methods in this class are safe for use by multiple concurrent
  * threads.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonReaderFactory {
@@ -85,5 +83,5 @@
      * Creates a JSON reader from a byte stream. The character encoding of
      * the stream is determined as described in
-     * <a href="http://tools.ietf.org/rfc/rfc4627.txt">RFC 4627</a>.
+     * <a href="http://tools.ietf.org/rfc/rfc7159.txt">RFC 7159</a>.
      * The reader is configured with the factory configuration.
      *
Index: trunk/src/javax/json/JsonString.java
===================================================================
--- trunk/src/javax/json/JsonString.java	(revision 13230)
+++ trunk/src/javax/json/JsonString.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -43,6 +43,4 @@
 /**
  * An immutable JSON string value.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonString extends JsonValue {
Index: trunk/src/javax/json/JsonStructure.java
===================================================================
--- trunk/src/javax/json/JsonStructure.java	(revision 13230)
+++ trunk/src/javax/json/JsonStructure.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -44,7 +44,19 @@
  * Super type for the two structured types in JSON ({@link JsonObject object}s
  * and {@link JsonArray array}s).
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonStructure extends JsonValue {
+
+    /**
+     * Get the value referenced by the provided JSON Pointer in the JsonStructure.
+     *
+     * @param jsonPointer the JSON Pointer
+     * @return the {@code JsonValue} at the referenced location
+     * @throws JsonException if the JSON Pointer is malformed, or if it references
+     *     a non-existing member or value.
+     *
+     * @since 1.1
+     */
+    default public JsonValue getValue(String jsonPointer) {
+        return Json.createPointer(jsonPointer).getValue(this);
+    }
 }
Index: trunk/src/javax/json/JsonValue.java
===================================================================
--- trunk/src/javax/json/JsonValue.java	(revision 13230)
+++ trunk/src/javax/json/JsonValue.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -44,15 +44,27 @@
  * <code>JsonValue</code> represents an immutable JSON value.
  *
- * 
+ *
  * <p>A JSON value is one of the following:
  * an object ({@link JsonObject}), an array ({@link JsonArray}),
  * a number ({@link JsonNumber}), a string ({@link JsonString}),
- * {@code true} ({@link JsonValue#TRUE JsonValue.TRUE}), {@code false} 
+ * {@code true} ({@link JsonValue#TRUE JsonValue.TRUE}), {@code false}
  * ({@link JsonValue#FALSE JsonValue.FALSE}),
  * or {@code null} ({@link JsonValue#NULL JsonValue.NULL}).
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonValue {
+
+    /**
+     * The empty JSON object.
+     *
+     * @since 1.1
+     */
+    static final JsonObject EMPTY_JSON_OBJECT = new EmptyObject();
+
+    /**
+     * The empty JSON array.
+     *
+     * @since 1.1
+     */
+    static final JsonArray EMPTY_JSON_ARRAY = new EmptyArray();
 
     /**
@@ -99,149 +111,15 @@
      * JSON null value.
      */
-    static final JsonValue NULL = new JsonValue() {
-        @Override
-        public ValueType getValueType() {
-            return ValueType.NULL;
-        }
-
-        /**
-         * Compares the specified object with this {@link JsonValue#NULL}
-         * object for equality. Returns {@code true} if and only if the
-         * specified object is also a {@code JsonValue}, and their
-         * {@link #getValueType()} objects are <i>equal</i>.
-         *
-         * @param obj the object to be compared for equality with this 
-         *      {@code JsonValue}
-         * @return {@code true} if the specified object is equal to this 
-         *      {@code JsonValue}
-         */
-        @Override
-        public boolean equals(Object obj) {
-            if (obj instanceof JsonValue) {
-                return getValueType().equals(((JsonValue)obj).getValueType());
-            }
-            return false;
-        }
-
-        /**
-         * Returns the hash code value for this {@link JsonValue#NULL} object.
-         * The hash code of the {@link JsonValue#NULL} object is defined to be
-         * its {@link #getValueType()} object's hash code.
-         *
-         * @return the hash code value for this JsonString object
-         */
-        @Override
-        public int hashCode() {
-            return ValueType.NULL.hashCode();
-        }
-
-        /**
-         * Returns a "null" string.
-         *
-         * @return "null"
-         */
-        @Override
-        public String toString() {
-            return "null";
-        }
-    };
+    static final JsonValue NULL = new JsonValueImpl(ValueType.NULL);
 
     /**
      * JSON true value.
      */
-    static final JsonValue TRUE = new JsonValue() {
-        @Override
-        public ValueType getValueType() {
-            return ValueType.TRUE;
-        }
-
-        /**
-         * Compares the specified object with this {@link JsonValue#TRUE}
-         * object for equality. Returns {@code true} if and only if the
-         * specified object is also a JsonValue, and their
-         * {@link #getValueType()} objects are <i>equal</i>.
-         *
-         * @param obj the object to be compared for equality with this JsonValue.
-         * @return {@code true} if the specified object is equal to this JsonValue.
-         */
-        @Override
-        public boolean equals(Object obj) {
-            if (obj instanceof JsonValue) {
-                return getValueType().equals(((JsonValue)obj).getValueType());
-            }
-            return false;
-        }
-
-        /**
-         * Returns the hash code value for this {@link JsonValue#TRUE} object.
-         * The hash code of the {@link JsonValue#TRUE} object is defined to be
-         * its {@link #getValueType()} object's hash code.
-         *
-         * @return the hash code value for this JsonString object
-         */
-        @Override
-        public int hashCode() {
-            return ValueType.TRUE.hashCode();
-        }
-
-        /**
-         * Returns "true" string
-         *
-         * @return "true"
-         */
-        @Override
-        public String toString() {
-            return "true";
-        }
-    };
+    static final JsonValue TRUE = new JsonValueImpl(ValueType.TRUE);
 
     /**
-     * JSON false value
+     * JSON false value.
      */
-    static final JsonValue FALSE = new JsonValue() {
-        @Override
-        public ValueType getValueType() {
-            return ValueType.FALSE;
-        }
-
-        /**
-         * Compares the specified object with this {@link JsonValue#FALSE}
-         * object for equality. Returns {@code true} if and only if the
-         * specified object is also a JsonValue, and their
-         * {@link #getValueType()} objects are <i>equal</i>.
-         *
-         * @param obj the object to be compared for equality with this JsonValue
-         * @return {@code true} if the specified object is equal to this JsonValue
-         */
-        @Override
-        public boolean equals(Object obj) {
-            if (obj instanceof JsonValue) {
-                return getValueType().equals(((JsonValue)obj).getValueType());
-            }
-            return false;
-        }
-
-        /**
-         * Returns the hash code value for this {@link JsonValue#FALSE} object.
-         * The hash code of the {@link JsonValue#FALSE} object is defined to be
-         * its {@link #getValueType()} object's hash code.
-         *
-         * @return the hash code value for this JsonString object
-         */
-        @Override
-        public int hashCode() {
-            return ValueType.FALSE.hashCode();
-        }
-
-        /**
-         * Returns "false" string
-         *
-         * @return "false"
-         */
-        @Override
-        public String toString() {
-            return "false";
-        }
-    };
+    static final JsonValue FALSE = new JsonValueImpl(ValueType.FALSE);
 
     /**
@@ -251,4 +129,28 @@
      */
     ValueType getValueType();
+
+    /**
+     * Return the JsonValue as a JsonObject
+     *
+     * @return the JsonValue as a JsonObject
+     * @throws ClassCastException if the JsonValue is not a JsonObject
+     *
+     * @since 1.1
+     */
+    default JsonObject asJsonObject() {
+        return JsonObject.class.cast(this);
+    }
+
+    /**
+     * Return the JsonValue as a JsonArray
+     *
+     * @return the JsonValue as a JsonArray
+     * @throws ClassCastException if the JsonValue is not a JsonArray
+     *
+     * @since 1.1
+     */
+    default JsonArray asJsonArray() {
+        return JsonArray.class.cast(this);
+    }
 
     /**
Index: trunk/src/javax/json/JsonValueImpl.java
===================================================================
--- trunk/src/javax/json/JsonValueImpl.java	(revision 13231)
+++ trunk/src/javax/json/JsonValueImpl.java	(revision 13231)
@@ -0,0 +1,107 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2016-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json;
+
+import java.io.Serializable;
+
+/**
+ * Private implementation of {@link JsonValue} for simple {@link ValueType}s
+ * allowing their usage in constants which are better to implement {@link Serializable}.
+ *
+ * @author Lukas Jungmann
+ */
+final class JsonValueImpl implements JsonValue, Serializable {
+
+    private final ValueType valueType;
+
+    JsonValueImpl(ValueType valueType) {
+        this.valueType = valueType;
+    }
+
+    /**
+     * Returns the value type of this JSON value.
+     *
+     * @return JSON value type
+     */
+    @Override
+    public ValueType getValueType() {
+        return valueType;
+    }
+
+    /**
+     * Compares the specified object with this {@link JsonValue}
+     * object for equality. Returns {@code true} if and only if the
+     * specified object is also a JsonValue, and their
+     * {@link #getValueType()} objects are <i>equal</i>.
+     *
+     * @param obj the object to be compared for equality with this JsonValue
+     * @return {@code true} if the specified object is equal to this
+     * JsonValue
+     */
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof JsonValue) {
+            return getValueType().equals(((JsonValue) obj).getValueType());
+        }
+        return false;
+    }
+
+    /**
+     * Returns the hash code value for this {@link JsonValue} object.
+     * The hash code of the {@link JsonValue} object is defined to be
+     * its {@link #getValueType()} object's hash code.
+     *
+     * @return the hash code value for this {@link JsonValue} object
+     */
+    @Override
+    public int hashCode() {
+        return valueType.hashCode();
+    }
+
+    @Override
+    public String toString() {
+        return valueType.name().toLowerCase();
+    }
+
+}
Index: trunk/src/javax/json/JsonWriter.java
===================================================================
--- trunk/src/javax/json/JsonWriter.java	(revision 13230)
+++ trunk/src/javax/json/JsonWriter.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -51,5 +51,4 @@
  *
  * <p>
- * <a id="JsonWriterExample1"/>
  * The following example demonstrates how write an empty JSON object:
  * <pre>
@@ -74,6 +73,4 @@
  * </code>
  * </pre>
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonWriter extends  /*Auto*/Closeable {
@@ -126,4 +123,23 @@
      * cause of JsonException)
      */
+
+    /**
+     * Writes the specified {@link JsonValue} to the output source.
+     * method needs to be called only once for a write instance.
+     *
+     * @param value a {@code JsonValue} to be written to the output
+     *              source
+     * @throws JsonException if the specified JSON object cannot be
+     *     written due to i/o error (IOException would be cause of
+     *     JsonException)
+     * @throws IllegalStateException if writeArray, writeObject, write
+     *     or close method is already called
+     *
+     * @since 1.1
+     */
+    default void write(JsonValue value) {
+        throw new UnsupportedOperationException();
+    }
+
     @Override
     void close();
Index: trunk/src/javax/json/JsonWriterFactory.java
===================================================================
--- trunk/src/javax/json/JsonWriterFactory.java	(revision 13230)
+++ trunk/src/javax/json/JsonWriterFactory.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -68,6 +68,4 @@
  * <p> All the methods in this class are safe for use by multiple concurrent
  * threads.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonWriterFactory {
Index: trunk/src/javax/json/package-info.java
===================================================================
--- trunk/src/javax/json/package-info.java	(revision 13230)
+++ trunk/src/javax/json/package-info.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -51,7 +51,7 @@
  * ordered sequence of zero or more values from the model.
  *
- * <p>The object model API uses builder patterns to create these object models. 
- * The classes {@link javax.json.JsonObjectBuilder} and 
- * {@link javax.json.JsonArrayBuilder} provide methods to create models
+ * <p>The object model API uses builder patterns to create and modify
+ * these object models. The classes {@link javax.json.JsonObjectBuilder} and 
+ * {@link javax.json.JsonArrayBuilder} provide methods to create and modify models
  * of type {@code JsonObject} and {@code JsonArray} respectively.
  *
@@ -59,7 +59,11 @@
  * the class {@link javax.json.JsonReader}. Similarly, these object models
  * can be written to an output source using the class {@link javax.json.JsonWriter}.
- *
- * @since JSON Processing 1.0
- * @author Jitendra Kotamraju
+ * <p>
+ * This package includes several classes that implement other JSON related
+ * standards: <a href="http://tools.ietf.org/html/rfc6901">JSON Pointer</a>,
+ * <a Href="http://tools.ietf.org/html/rfc6902">JSON Patch</a>, and
+ * <a Href="http://tools.ietf.org/html/rfc7396">JSON Merge Patch</a>.
+ * They can be used to retrieve, transform or manipulate values in an
+ * object model.
  */
 package javax.json;
Index: trunk/src/javax/json/spi/JsonProvider.java
===================================================================
--- trunk/src/javax/json/spi/JsonProvider.java	(revision 13230)
+++ trunk/src/javax/json/spi/JsonProvider.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -50,7 +50,11 @@
 import java.io.Reader;
 import java.io.Writer;
+import java.util.Collection;
 import java.util.Iterator;
 import java.util.Map;
 import java.util.ServiceLoader;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.util.Optional;
 
 /**
@@ -61,5 +65,4 @@
  *
  * @see ServiceLoader
- * @author Jitendra Kotamraju
  */
 public abstract class JsonProvider {
@@ -76,8 +79,8 @@
 
     /**
-     *
      * Creates a JSON provider object. The provider is loaded using the
      * {@link ServiceLoader#load(Class)} method. If there are no available
      * service providers, this method returns the default service provider.
+     * Users are recommended to cache the result of this method.
      *
      * @see ServiceLoader
@@ -90,8 +93,7 @@
             return it.next();
         }
-
         try {
             Class<?> clazz = Class.forName(DEFAULT_PROVIDER);
-            return (JsonProvider)clazz.newInstance();
+            return (JsonProvider) clazz.newInstance();
         } catch (ClassNotFoundException x) {
             throw new JsonException(
@@ -115,5 +117,5 @@
      * Creates a JSON parser from the specified byte stream.
      * The character encoding of the stream is determined
-     * as defined in <a href="http://tools.ietf.org/rfc/rfc4627.txt">RFC 4627
+     * as defined in <a href="http://tools.ietf.org/rfc/rfc7159.txt">RFC 7159
      * </a>.
      *
@@ -193,5 +195,5 @@
      * Creates a JSON reader from a byte stream. The character encoding of
      * the stream is determined as described in
-     * <a href="http://tools.ietf.org/rfc/rfc4627.txt">RFC 4627</a>.
+     * <a href="http://tools.ietf.org/rfc/rfc7159.txt">RFC 7159</a>.
      *
      * @param in a byte stream from which JSON is to be read
@@ -246,5 +248,5 @@
 
     /**
-     * Creates a JSON object builder
+     * Creates a JSON object builder.
      *
      * @return a JSON object builder
@@ -253,9 +255,166 @@
 
     /**
-     * Creates a JSON array builder
+     * Creates a JSON object builder, initialized with the specified object.
+     *
+     * @param object the initial JSON object in the builder
+     * @return a JSON object builder
+     *
+     * @since 1.1
+     */
+    public JsonObjectBuilder createObjectBuilder(JsonObject object) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JSON object builder, initialized with the data from specified {@code map}.
+     * If the @{code map} contains {@link Optional}s then resulting JSON object builder
+     * contains the key from the {@code map} only if the {@link Optional} is not empty.
+     *
+     * @param map the initial object in the builder
+     * @return a JSON object builder
+     * @exception IllegalArgumentException if the value from the {@code map} cannot be converted
+     *            to the corresponding {@link JsonValue}
+     *
+     * @since 1.1
+     */
+    public JsonObjectBuilder createObjectBuilder(Map<String, Object> map) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JSON array builder.
      *
      * @return a JSON array builder
      */
     public abstract JsonArrayBuilder createArrayBuilder();
+
+    /**
+     * Creates a JSON array builder, initialized with the specified array.
+     *
+     * @param array the initial JSON array in the builder
+     * @return a JSON array builder
+     *
+     * @since 1.1
+     */
+    public JsonArrayBuilder createArrayBuilder(JsonArray array) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates JSON Pointer (<a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>)
+     * from given {@code jsonPointer} string.
+     * <ul>
+     *     <li>An empty {@code jsonPointer} string defines a reference to the target itself.</li>
+     *     <li>If the {@code jsonPointer} string is non-empty, it must be a sequence of '{@code /}' prefixed tokens.</li>
+     * </ul>
+     *
+     * @param jsonPointer the JSON Pointer string
+     * @throws NullPointerException if {@code jsonPointer} is {@code null}
+     * @throws JsonException if {@code jsonPointer} is not a valid JSON Pointer
+     * @return a JSON Pointer
+     *
+     * @since 1.1
+     */
+    public JsonPointer createPointer(String jsonPointer) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JSON Patch builder (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>).
+     *
+     * @return a JSON Patch builder
+     *
+     * @since 1.1
+     */
+    public JsonPatchBuilder createPatchBuilder() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JSON Patch builder
+     * (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>),
+     * initialized with the specified operations.
+     *
+     * @param array the initial patch operations
+     * @return a JSON Patch builder
+     *
+     * @since 1.1
+     */
+    public JsonPatchBuilder createPatchBuilder(JsonArray array) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JSON Patch (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>)
+     * from the specified operations.
+     *
+     * @param array patch operations
+     * @return a JSON Patch
+     *
+     * @since 1.1
+     */
+    public JsonPatch createPatch(JsonArray array) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Generates a JSON Patch (<a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>)
+     * from the source and target {@code JsonStructure}.
+     * The generated JSON Patch need not be unique.
+     *
+     * @param source the source
+     * @param target the target, must be the same type as the source
+     * @return a JSON Patch which when applied to the source, yields the target
+     *
+     * @since 1.1
+     */
+    public JsonPatch createDiff(JsonStructure source, JsonStructure target) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates JSON Merge Patch (<a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>)
+     * from specified {@code JsonValue}.
+     *
+     * @param patch the patch
+     * @return a JSON Merge Patch
+     *
+     * @since 1.1
+     */
+    public JsonMergePatch createMergePatch(JsonValue patch) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Generates a JSON Merge Patch (<a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>)
+     * from the source and target {@code JsonValue}s
+     * which when applied to the {@code source}, yields the {@code target}.
+     *
+     * @param source the source
+     * @param target the target
+     * @return a JSON Merge Patch
+     *
+     * @since 1.1
+     */
+    public JsonMergePatch createMergeDiff(JsonValue source, JsonValue target) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JSON array builder, initialized with the content of specified {@code collection}.
+     * If the @{code collection} contains {@link Optional}s then resulting JSON array builder
+     * contains the value from the {@code collection} only if the {@link Optional} is not empty.
+     *
+     * @param collection the initial data for the builder
+     * @return a JSON array builder
+     * @exception IllegalArgumentException if the value from the {@code collection} cannot be converted
+     *            to the corresponding {@link JsonValue}
+     *
+     * @since 1.1
+     */
+    public JsonArrayBuilder createArrayBuilder(Collection<?> collection) {
+        throw new UnsupportedOperationException();
+    }
+
 
     /**
@@ -272,3 +431,74 @@
     public abstract JsonBuilderFactory createBuilderFactory(Map<String,?> config);
 
+    /**
+     * Creates a JsonString.
+     *
+     * @param value a JSON string
+     * @return the JsonString for the string
+     *
+     * @since 1.1
+     */
+    public JsonString createValue(String value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public JsonNumber createValue(int value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public JsonNumber createValue(long value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public JsonNumber createValue(double value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public JsonNumber createValue(BigDecimal value) {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Creates a JsonNumber.
+     *
+     * @param value a JSON number
+     * @return the JsonNumber for the number
+     *
+     * @since 1.1
+     */
+    public JsonNumber createValue(BigInteger value) {
+        throw new UnsupportedOperationException();
+    }
 }
Index: trunk/src/javax/json/spi/package-info.java
===================================================================
--- trunk/src/javax/json/spi/package-info.java	(revision 13230)
+++ trunk/src/javax/json/spi/package-info.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -53,5 +53,4 @@
  *
  * @since JSON Processing 1.0
- * @author Jitendra Kotamraju
  */
 package javax.json.spi;
Index: trunk/src/javax/json/stream/JsonCollectors.java
===================================================================
--- trunk/src/javax/json/stream/JsonCollectors.java	(revision 13231)
+++ trunk/src/javax/json/stream/JsonCollectors.java	(revision 13231)
@@ -0,0 +1,184 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package javax.json.stream;
+
+import java.util.Map;
+import java.util.HashMap;
+import java.util.stream.Collector;
+import java.util.function.BinaryOperator;
+import java.util.function.Function;
+import java.util.function.BiConsumer;
+
+import javax.json.Json;
+import javax.json.JsonArray;
+import javax.json.JsonArrayBuilder;
+import javax.json.JsonObject;
+import javax.json.JsonObjectBuilder;
+import javax.json.JsonValue;
+import javax.json.JsonException;
+
+/**
+ * This class contains some implementations of {@code java.util.stream.Collector} for accumulating
+ * {@link JsonValue}s into {@link JsonArray} and {@link JsonObject}.
+ *
+ * @since 1.1
+ */
+
+public final class JsonCollectors {
+
+    private JsonCollectors() {
+    }
+
+    /**
+     * Constructs a {@code java.util.stream.Collector} that accumulates the input {@code JsonValue}
+     * elements into a {@code JsonArray}.
+     *
+     * @return the constructed Collector
+     */
+    public static Collector<JsonValue, JsonArrayBuilder, JsonArray> toJsonArray() {
+        return Collector.of(
+                Json::createArrayBuilder,
+                JsonArrayBuilder::add,
+                JsonArrayBuilder::addAll,
+                JsonArrayBuilder::build);
+    }
+
+    /**
+     * Constructs a {@code java.util.stream.Collector} that accumulates the input {@code Map.Entry<String,JsonValue>}
+     * elements into a {@code JsonObject}.
+     *
+     * @return the constructed Collector
+     */
+    public static Collector<Map.Entry<String, JsonValue>, JsonObjectBuilder, JsonObject> toJsonObject() {
+        return Collector.of(
+                Json::createObjectBuilder,
+                (JsonObjectBuilder b, Map.Entry<String, JsonValue> v) -> b.add(v.getKey(), v.getValue()),
+                JsonObjectBuilder::addAll,
+                JsonObjectBuilder::build);
+    }
+
+    /**
+     * Constructs a {@code java.util.stream.Collector} that accumulates the input {@code JsonValue}
+     * elements into a {@code JsonObject}.  The name/value pairs of the {@code JsonObject} are computed
+     * by applying the provided mapping functions.
+     *
+     * @param keyMapper a mapping function to produce names.
+     * @param valueMapper a mapping function to produce values
+     * @return the constructed Collector
+     */
+    public static Collector<JsonValue, JsonObjectBuilder, JsonObject>
+                toJsonObject(Function<JsonValue, String> keyMapper,
+                             Function<JsonValue, JsonValue> valueMapper) {
+        return Collector.of(
+                Json::createObjectBuilder,
+                (b, v) -> b.add(keyMapper.apply(v), valueMapper.apply(v)),
+                JsonObjectBuilder::addAll,
+                JsonObjectBuilder::build,
+                Collector.Characteristics.UNORDERED);
+    }
+
+    /**
+     * Constructs a {@code java.util.stream.Collector} that implements a "group by" operation on the
+     * input {@code JsonValue} elements. A classifier function maps the input {@code JsonValue}s to keys, and
+     * the {@code JsonValue}s are partitioned into groups according to the value of the key.
+     * A reduction operation is performed on the {@code JsonValue}s in each group, using the
+     * downstream {@code Collector}. For each group, the key and the results of the reduction operation
+     * become the name/value pairs of the resultant {@code JsonObject}.
+     *
+     * @param <T> the intermediate accumulation {@code JsonArrayBuilder} of the downstream collector
+     * @param classifier a function mapping the input {@code JsonValue}s to a String, producing keys
+     * @param downstream a {@code Collector} that implements a reduction operation on the
+     *        {@code JsonValue}s in each group.
+     * @return the constructed {@code Collector}
+     */
+    public static <T extends JsonArrayBuilder> Collector<JsonValue, Map<String, T>, JsonObject>
+                groupingBy(Function<JsonValue, String> classifier,
+                           Collector<JsonValue, T, JsonArray> downstream) {
+
+        BiConsumer<Map<String, T>, JsonValue> accumulator =
+            (map, value) -> {
+                String key = classifier.apply(value);
+                if (key == null) {
+                    throw new JsonException("element cannot be mapped to a null key");
+                }
+                // Build a map of key to JsonArrayBuilder
+                T arrayBuilder =
+                    map.computeIfAbsent(key, v->downstream.supplier().get());
+                // Add elements from downstream Collector to the arrayBuilder.
+                downstream.accumulator().accept(arrayBuilder, value);
+            };
+        Function<Map<String, T>, JsonObject> finisher =
+            map -> {
+                // transform the map of name: JsonArrayBuilder to
+                //                      name: JsonArray
+                // using the downstream collector for reducing the JsonArray
+                JsonObjectBuilder objectBuilder = Json.createObjectBuilder();
+                map.forEach((k, v) -> {
+                    JsonArray array = downstream.finisher().apply(v);
+                    objectBuilder.add(k, array);
+                });
+                return objectBuilder.build();
+            };
+        BinaryOperator<Map<String, T>> combiner =
+            (map1, map2) -> {
+                map1.putAll(map2);
+                return map1;
+            };
+        return Collector.of(HashMap::new, accumulator, combiner, finisher,
+            Collector.Characteristics.UNORDERED);
+    }
+
+    /**
+     * Constructs a {@code java.util.stream.Collector} that implements a "group by" operation on the
+     * input {@code JsonValue} elements. A classifier function maps the input {@code JsonValue}s to keys, and
+     * the {@code JsonValue}s are partitioned into groups according to the value of the key.
+     * The {@code JsonValue}s in each group are added to a {@code JsonArray}.  The key and the
+     * {@code JsonArray} in each group becomes the name/value pair of the resultant {@code JsonObject}.
+     *
+     * @param classifier a function mapping the input {@code JsonValue}s to a String, producing keys
+     * @return the constructed {@code Collector}
+     */
+    public static Collector<JsonValue, Map<String, JsonArrayBuilder>, JsonObject>
+                groupingBy(Function<JsonValue, String> classifier) {
+        return groupingBy(classifier, toJsonArray());
+    }
+}
+
Index: trunk/src/javax/json/stream/JsonGenerationException.java
===================================================================
--- trunk/src/javax/json/stream/JsonGenerationException.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonGenerationException.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -46,6 +46,4 @@
  * {@code JsonGenerationException} indicates an incorrect JSON is
  * being generated.
- *
- * @author Jitendra Kotamraju
  */
 public class JsonGenerationException extends JsonException {
Index: trunk/src/javax/json/stream/JsonGenerator.java
===================================================================
--- trunk/src/javax/json/stream/JsonGenerator.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonGenerator.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -98,7 +98,15 @@
  * </pre>
  *
+ * <p>
+ * Other JSON values (that are not JSON objects or arrays) can be created
+ * by calling the appropiate {@code write} methods.
+ * <p>
+ * The following example shows how to generate a JSON string:
+ * <pre><code>
+ * JsonGenerator generator = ...;
+ * generator.write("message").close();
+ * </code></pre>
+ *
  * {@code JsonGenerator} methods can be chained as in the following example:
- * <p>
- * <a id="JsonGeneratorExample3"/>
  * <pre>
  * <code>
@@ -130,5 +138,4 @@
  *
  * The example code above generates the following JSON (or equivalent):
- * <p>
  * <pre>
  * <code>
@@ -150,9 +157,8 @@
  *
  * The generated JSON text must strictly conform to the grammar defined in
- * <a href="http://www.ietf.org/rfc/rfc4627.txt">RFC 4627</a>.
+ * <a href="http://www.ietf.org/rfc/rfc7159.txt">RFC 7159</a>.
  *
  * @see javax.json.Json
  * @see JsonGeneratorFactory
- * @author Jitendra Kotamraju
  */
 public interface JsonGenerator extends Flushable, /*Auto*/Closeable {
@@ -167,5 +173,5 @@
      * Writes the JSON start object character. It starts a new child object
      * context within which JSON name/value pairs can be written to the object.
-     * This method is valid only in an array context or in no context (when a
+     * This method is valid only in an array context, field context or in no context (when a
      * context is not yet started). This method can only be called once in
      * no context.
@@ -174,5 +180,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is called within an 
+     * @throws JsonGenerationException if this method is called within an
      *      object context or if it is called more than once in no context.
      */
@@ -188,13 +194,31 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *     object context
      */
     JsonGenerator writeStartObject(String name);
+
+    /**
+     * Writes the JSON name with a colon. It starts a field context, in which valid
+     * options are writing a value, starting an object or an array.
+     *
+     * Writing value closes field context, if object or array is started after field name,
+     * field context will be closed after object/array close.
+     *
+     * @param name name of json field
+     * @return this generator
+     * @throws javax.json.JsonException if an i/o error occurs (IOException
+     * would be cause of JsonException)
+     * @throws JsonGenerationException if this method is not called within an
+     *     object context
+     *
+     * @since 1.1
+     */
+    JsonGenerator writeKey(String name);
 
     /**
      * Writes the JSON start array character. It starts a new child array
      * context within which JSON values can be written to the array. This
-     * method is valid only in an array context or in no context (when a
+     * method is valid only in an array context, field context or in no context (when a
      * context is not yet started). This method can only be called once in
      * no context.
@@ -203,5 +227,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is called within an 
+     * @throws JsonGenerationException if this method is called within an
      *      object context or if called more than once in no context
      */
@@ -217,5 +241,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within 
+     * @throws JsonGenerationException if this method is not called within
      *      an object context
      */
@@ -232,5 +256,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context
      */
@@ -248,5 +272,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context
      */
@@ -266,5 +290,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context.
      */
@@ -283,5 +307,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context.
      */
@@ -301,5 +325,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context.
      */
@@ -319,5 +343,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context.
      */
@@ -337,5 +361,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws NumberFormatException if the value is Not-a-Number(NaN) or infinity.
+     * @throws NumberFormatException if the value is Not-a-Number (NaN) or infinity.
      * @throws JsonGenerationException if this method is not called within an
      *      object context
@@ -345,5 +369,5 @@
     /**
      * Writes a JSON name/boolean value pair in the current object context.
-     * If value is true, it writes the JSON {@code true} value, otherwise 
+     * If value is true, it writes the JSON {@code true} value, otherwise
      * it writes the JSON {@code false} value.
      *
@@ -369,5 +393,5 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
+     * @throws JsonGenerationException if this method is not called within an
      *      object context
      */
@@ -376,8 +400,9 @@
     /**
      * Writes the end of the current context. If the current context is
-     * an array context, this method writes the end-of-array character (']'). 
+     * an array context, this method writes the end-of-array character (']').
      * If the current context is an object context, this method writes the
      * end-of-object character ('}'). After writing the end of the current
      * context, the parent context becomes the new current context.
+     * If parent context is field context, it is closed.
      *
      * @return this generator
@@ -390,12 +415,12 @@
     /**
      * Writes the specified value as a JSON value within
-     * the current array context.
-     *
-     * @param value a value to be written in current JSON array
-     * @return this generator
-     * @throws javax.json.JsonException if an i/o error occurs (IOException
-     * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context.
+     * the current array, field or root context.
+     *
+     * @param value a value to be written in current JSON array
+     * @return this generator
+     * @throws javax.json.JsonException if an i/o error occurs (IOException
+     * would be cause of JsonException)
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      */
     JsonGenerator write(JsonValue value);
@@ -403,12 +428,12 @@
     /**
      * Writes the specified value as a JSON string value within
-     * the current array context.
-     *
-     * @param value a value to be written in current JSON array
-     * @return this generator
-     * @throws javax.json.JsonException if an i/o error occurs (IOException
-     * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
+     * the current array, field or root context.
+     *
+     * @param value a value to be written in current JSON array
+     * @return this generator
+     * @throws javax.json.JsonException if an i/o error occurs (IOException
+     * would be cause of JsonException)
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      */
     JsonGenerator write(String value);
@@ -416,5 +441,5 @@
     /**
      * Writes the specified value as a JSON number value within
-     * the current array context. The specified value's {@code toString()}
+     * the current array, field or root context. The specified value's {@code toString()}
      * is used as the the text value for writing.
      *
@@ -423,6 +448,6 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      *
      * @see javax.json.JsonNumber
@@ -432,5 +457,5 @@
     /**
      * Writes the specified value as a JSON number value within
-     * the current array context. The string {@code new BigDecimal(value).toString()}
+     * the current array, field or root context. The string {@code new BigDecimal(value).toString()}
      * is used as the text value for writing.
      *
@@ -439,6 +464,6 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      *
      * @see javax.json.JsonNumber
@@ -448,5 +473,5 @@
     /**
      * Writes the specified value as a JSON number value within
-     * the current array context. The string {@code new BigDecimal(value).toString()}
+     * the current array, field or root context. The string {@code new BigDecimal(value).toString()}
      * is used as the text value for writing.
      *
@@ -455,6 +480,6 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      */
     JsonGenerator write(int value);
@@ -462,5 +487,5 @@
     /**
      * Writes the specified value as a JSON number value within
-     * the current array context. The string {@code new BigDecimal(value).toString()}
+     * the current array, field or root context. The string {@code new BigDecimal(value).toString()}
      * is used as the text value for writing.
      *
@@ -469,6 +494,6 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      */
     JsonGenerator write(long value);
@@ -476,5 +501,5 @@
     /**
      * Writes the specified value as a JSON number value within the current
-     * array context. The string {@code BigDecimal.valueOf(value).toString()}
+     * array, field or root context. The string {@code BigDecimal.valueOf(value).toString()}
      * is used as the text value for writing.
      *
@@ -483,13 +508,13 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
-     * @throws NumberFormatException if the value is Not-a-Number(NaN) or infinity.
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
+     * @throws NumberFormatException if the value is Not-a-Number (NaN) or infinity.
      */
     JsonGenerator write(double value);
 
     /**
-     * Writes a JSON true or false value within the current array context.
-     * If value is true, this method writes the JSON {@code true} value, 
+     * Writes a JSON true or false value within the current array, field or root context.
+     * If value is true, this method writes the JSON {@code true} value,
      * otherwise it writes the JSON {@code false} value.
      *
@@ -498,22 +523,22 @@
      * @throws javax.json.JsonException if an i/o error occurs (IOException
      * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context.
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      */
     JsonGenerator write(boolean value);
 
     /**
-     * Writes a JSON null value within the current array context.
-     *
-     * @return this generator
-     * @throws javax.json.JsonException if an i/o error occurs (IOException
-     * would be cause of JsonException)
-     * @throws JsonGenerationException if this method is not called within an 
-     *      array context
+     * Writes a JSON null value within the current array, field or root context.
+     *
+     * @return this generator
+     * @throws javax.json.JsonException if an i/o error occurs (IOException
+     * would be cause of JsonException)
+     * @throws JsonGenerationException if this method is not called within an
+     *      array or root context.
      */
     JsonGenerator writeNull();
 
     /**
-     * Closes this generator and frees any resources associated with it. 
+     * Closes this generator and frees any resources associated with it.
      * This method closes the underlying output source.
      *
Index: trunk/src/javax/json/stream/JsonGeneratorFactory.java
===================================================================
--- trunk/src/javax/json/stream/JsonGeneratorFactory.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonGeneratorFactory.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -67,6 +67,4 @@
  * <p> All the methods in this class are safe for use by multiple concurrent
  * threads.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonGeneratorFactory {
@@ -77,4 +75,5 @@
      *
      * @param writer i/o writer to which JSON is written
+     * @return the created JSON generator
      */
     JsonGenerator createGenerator(Writer writer);
@@ -86,4 +85,5 @@
      *
      * @param out i/o stream to which JSON is written
+     * @return the created JSON generator
      */
     JsonGenerator createGenerator(OutputStream out);
@@ -96,4 +96,5 @@
      * @param out i/o stream to which JSON is written
      * @param charset a charset
+     * @return the created JSON generator
      */
     JsonGenerator createGenerator(OutputStream out, Charset charset);
Index: trunk/src/javax/json/stream/JsonLocation.java
===================================================================
--- trunk/src/javax/json/stream/JsonLocation.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonLocation.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -52,6 +52,4 @@
  * {@link javax.json.JsonArray JsonArray} input source, all the methods in
  * this class return -1.
- *
- * @author Jitendra Kotamraju
  * @see JsonParser
  * @see JsonParsingException
@@ -60,14 +58,14 @@
 
     /**
-     * Return the line number for the current JSON event in the input source.
+     * Return the line number (starts with 1 for the first line) for the current JSON event in the input source.
      *
-     * @return the line number or -1 if none is available
+     * @return the line number (starts with 1 for the first line) or -1 if none is available
      */
     long getLineNumber();
 
     /**
-     * Return the column number for the current JSON event in the input source.
+     * Return the column number (starts with 1 for the first column) for the current JSON event in the input source.
      *
-     * @return the column number or -1 if none is available
+     * @return the column number (starts with 1 for the first column) or -1 if none is available
      */
     long getColumnNumber();
Index: trunk/src/javax/json/stream/JsonParser.java
===================================================================
--- trunk/src/javax/json/stream/JsonParser.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonParser.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -44,8 +44,16 @@
 import java.io.Closeable;
 import java.math.BigDecimal;
+import java.util.stream.Stream;
+import java.util.Map;
+
+import javax.json.JsonValue;
+import javax.json.JsonObject;
+import javax.json.JsonArray;
 
 /**
  * Provides forward, read-only access to JSON data in a streaming way. This
- * is the most efficient way for reading JSON data. The class
+ * is the most efficient way for reading JSON data.
+ * This is the only way to parse and process JSON data that are too big to be loaded in memory.
+ * <p>The class
  * {@link javax.json.Json} contains methods to create parsers from input
  * sources ({@link java.io.InputStream} and {@link java.io.Reader}).
@@ -97,6 +105,4 @@
  *
  * <p>
- * <a id="JsonParserExample2"/>
- * <p>
  * <b>For example</b>, for the following JSON:
  * <pre>
@@ -113,5 +119,4 @@
  * locations below (marked in bold):
  *
- * <p>
  * <pre>
  * {<B>START_OBJECT</B>
@@ -124,11 +129,9 @@
  * </pre>
  *
- * <p>
- * The methods {@code next()} and {@code hasNext()} enable iteration over
+ * The methods {@link #next()} and {@link #hasNext()} enable iteration over
  * parser events to process JSON data. {@code JsonParser} provides get methods
  * to obtain the value at the current state of the parser. For example, the
  * following code shows how to obtain the value "John" from the JSON above:
  *
- * <p>
  * <pre>
  * <code>
@@ -140,7 +143,54 @@
  * </pre>
  *
+ * Starting in version 1.1, it is possible to build a partial JSON object
+ * model from the stream, at the current parser position.
+ * The methods {@link #getArray} and {@link #getObject} can be used to read in
+ * a {@code JsonArray} or {@code JsonObject}.  For example, the following code
+ * shows how to obtain the phoneNumber in a JsonArray, from the JSON above:
+ *
+ * <pre><code>
+ * while (parser.hasNext() {
+ *     Event event = parser.next();
+ *     if (event == JsonParser.Event.KEY_NAME ) {
+ *         String key = getString();
+ *         event = parser.next();
+ *         if (key.equals("phoneNumber") {
+ *             JsonArray phones = parser.getArray();
+ *         }
+ *     }
+ * }
+ * </code></pre>
+ *
+ * The methods {@link #getArrayStream} and {@link #getObjectStream} can be used
+ * to get a stream of the elements of a {@code JsonArray} or {@code JsonObject}.
+ * For example, the following code shows another way to obtain John's phoneNumber
+ * in a {@code JsonArray} :
+ *
+ * <pre>{@code
+ * Event event = parser.next(); // START_OBJECT
+ * JsonArray phones = (JsonArray)
+ *     parser.getObjectStream().filter(e->e.getKey().equals("phoneNumber"))
+ *                             .map(e->e.getValue())
+ *                             .findFirst()
+ *                             .get();
+ * }</pre>
+ *
+ * The methods {@link #skipArray} and {@link #skipObject} can be used to
+ * skip tokens and position the parser to {@code END_ARRAY} or
+ * {@code END_OBJECT}.
+ * <p>
+ * {@code JsonParser} can be used to parse sequence of JSON values that are not
+ * enclosed in a JSON array, e.g. { } { }. The following code demonstrates how
+ * to parse such sequence.
+ * <pre><code>
+ * JsonParser parser = Json.createParser(...);
+ * while (parser.hasNext) {
+ *     parser.next(); // advance parser state
+ *     JsonValue value = parser.getValue();
+ * }
+ * </code></pre>
+ *
  * @see javax.json.Json
  * @see JsonParserFactory
- * @author Jitendra Kotamraju
  */
 public interface JsonParser extends /*Auto*/Closeable {
@@ -223,4 +273,5 @@
      * @throws java.util.NoSuchElementException if there are no more parsing
      * states.
+     * @return the event for the next parsing state
      */
     Event next();
@@ -319,19 +370,133 @@
 
     /**
-     * getJsonValue(JsonObject.class) is valid in the START_OBJECT state and
-     * moves the cursor to END_OBJECT.
-     *
-     * getJsonValue(JsonArray.class) is valid in the START_ARRAY state
-     * and moves the cursor to END_ARRAY.
-     *
-     * getJsonValue(JsonString.class) is valid in the VALUE_STRING state.
-     *
-     * getJsonValue(JsonNumber.class) is valid in the VALUE_NUMBER state.
-     *
-     * @param clazz
-     * @return
-     *
-    public <T extends JsonValue> T getJsonValue(Class<T> clazz);
-     */
+     * Returns a {@code JsonObject} and advances the parser to the
+     * corresponding {@code END_OBJECT}.
+     *
+     * @return the {@code JsonObject} at the current parser position
+     *
+     * @throws IllegalStateException when the parser state is not
+     *     {@code START_OBJECT}
+     *
+     * @since 1.1
+     */
+    default public JsonObject getObject() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Returns a {@code JsonValue} at the current parser position.
+     * If the parser state is {@code START_ARRAY}, the behavior is
+     * the same as {@link #getArray}. If the parser state is
+     * {@code START_OBJECT}, the behavior is the same as
+     * {@link #getObject}. For all other cases, if applicable, the JSON value is
+     * read and returned.
+     *
+     * @return the {@code JsonValue} at the current parser position.
+     * @throws IllegalStateException when the parser state is
+     *     {@code END_OBJECT} or {@code END_ARRAY}
+     *
+     * @since 1.1
+     */
+    default public JsonValue getValue() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Returns a {@code JsonArray} and advance the parser to the
+     * the corresponding {@code END_ARRAY}.
+     *
+     * @return the {@code JsonArray} at the current parser position
+     *
+     * @throws IllegalStateException when the parser state is not
+     *     {@code START_ARRAY}
+     *
+     * @since 1.1
+     */
+    default public JsonArray getArray() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Returns a stream of the {@code JsonArray} elements.
+     * The parser state must be {@code START_ARRAY}.
+     * The elements are read lazily, on an as-needed basis, as
+     * required by the stream operations.
+     * If the stream operations do not consume
+     * all of the array elements, {@link skipArray} can be used to
+     * skip the unprocessed array elements.
+     *
+     * @return a stream of elements of the {@code JsonArray}
+     *
+     * @throws IllegalStateException when the parser state is not
+     *     {@code START_ARRAY}
+     *
+     * @since 1.1
+     */
+    default public Stream<JsonValue> getArrayStream() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Returns a stream of the {@code JsonObject}'s
+     * name/value pairs. The parser state must be {@code START_OBJECT}.
+     * The name/value pairs are read lazily, on an as-needed basis, as
+     * required by the stream operations.
+     * If the stream operations do not consume
+     * all of the object's name/value pairs, {@link skipObject} can be
+     * used to skip the unprocessed elements.
+     *
+     * @return a stream of name/value pairs of the {@code JsonObject}
+     *
+     * @throws IllegalStateException when the parser state is not
+     *     {@code START_OBJECT}
+     *
+     * @since 1.1
+     */
+    default public Stream<Map.Entry<String,JsonValue>> getObjectStream() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Returns a stream of {@code JsonValue} from a sequence of
+     * JSON values. The values are read lazily, on an as-needed basis,
+     * as needed by the stream operations.
+     *
+     * @return a Stream of {@code JsonValue}
+     *
+     * @throws IllegalStateException if the parser is in an array or object.
+     *
+     * @since 1.1
+     */
+    default public Stream<JsonValue> getValueStream() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Advance the parser to {@code END_ARRAY}.
+     * If the parser is in array context, i.e. it has previously
+     * encountered a {@code START_ARRAY} without encountering the
+     * corresponding {@code END_ARRAY}, the parser is advanced to
+     * the corresponding {@code END_ARRAY}.
+     * If the parser is not in any array context, nothing happens.
+     *
+     * @since 1.1
+     */
+    default public void skipArray() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Advance the parser to {@code END_OBJECT}.
+     * If the parser is in object context, i.e. it has previously
+     * encountered a {@code START_OBJECT} without encountering the
+     * corresponding {@code END_OBJECT}, the parser is advanced to
+     * the corresponding {@code END_OBJECT}.
+     * If the parser is not in any object context, nothing happens.
+     *
+     * @since 1.1
+     */
+    default public void skipObject() {
+        throw new UnsupportedOperationException();
+    }
 
     /**
@@ -344,4 +509,3 @@
     @Override
     void close();
-
 }
Index: trunk/src/javax/json/stream/JsonParserFactory.java
===================================================================
--- trunk/src/javax/json/stream/JsonParserFactory.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonParserFactory.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2011-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -69,6 +69,4 @@
  * <p> All the methods in this class are safe for use by multiple concurrent
  * threads.
- *
- * @author Jitendra Kotamraju
  */
 public interface JsonParserFactory {
@@ -78,4 +76,5 @@
      *
      * @param reader a i/o reader from which JSON is to be read
+     * @return the created JSON parser
      */
     JsonParser createParser(Reader reader);
@@ -84,7 +83,8 @@
      * Creates a JSON parser from the specified byte stream.
      * The character encoding of the stream is determined
-     * as specified in <a href="http://tools.ietf.org/rfc/rfc4627.txt">RFC 4627</a>.
+     * as specified in <a href="http://tools.ietf.org/rfc/rfc7159.txt">RFC 7159</a>.
      *
      * @param in i/o stream from which JSON is to be read
+     * @return the created JSON parser
      * @throws javax.json.JsonException if encoding cannot be determined
      *         or i/o error (IOException would be cause of JsonException)
@@ -99,4 +99,5 @@
      * @param in i/o stream from which JSON is to be read
      * @param charset a charset
+     * @return the created JSON parser
      */
     JsonParser createParser(InputStream in, Charset charset);
@@ -106,4 +107,5 @@
      *
      * @param obj a JSON object
+     * @return the created JSON parser
      */
     JsonParser createParser(JsonObject obj);
@@ -113,4 +115,5 @@
      *
      * @param array a JSON array
+     * @return the created JSON parser
      */
     JsonParser createParser(JsonArray array);
Index: trunk/src/javax/json/stream/JsonParsingException.java
===================================================================
--- trunk/src/javax/json/stream/JsonParsingException.java	(revision 13230)
+++ trunk/src/javax/json/stream/JsonParsingException.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -46,6 +46,4 @@
  * {@code JsonParsingException} is used when an incorrect JSON is
  * being parsed.
- *
- * @author Jitendra Kotamraju
  */
 public class JsonParsingException extends JsonException {
Index: trunk/src/javax/json/stream/package-info.java
===================================================================
--- trunk/src/javax/json/stream/package-info.java	(revision 13230)
+++ trunk/src/javax/json/stream/package-info.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -68,5 +68,4 @@
  *
  * @since JSON Processing 1.0
- * @author Jitendra Kotamraju
  */
 package javax.json.stream;
Index: trunk/src/org/glassfish/json/BufferPoolImpl.java
===================================================================
--- trunk/src/org/glassfish/json/BufferPoolImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/BufferPoolImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -82,6 +82,6 @@
 
         // overwrite the queue
-        ConcurrentLinkedQueue<char[]> d = new ConcurrentLinkedQueue<char[]>();
-        queue = new WeakReference<ConcurrentLinkedQueue<char[]>>(d);
+        ConcurrentLinkedQueue<char[]> d = new ConcurrentLinkedQueue<>();
+        queue = new WeakReference<>(d);
 
         return d;
Index: trunk/src/org/glassfish/json/JsonArrayBuilderImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonArrayBuilderImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonArrayBuilderImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -49,12 +49,16 @@
 import java.util.AbstractList;
 import java.util.ArrayList;
+import java.util.Collection;
 import java.util.Collections;
 import java.util.List;
+import java.util.Optional;
 
 /**
- * JsonArrayBuilder impl
+ * JsonArrayBuilder implementation
  *
  * @author Jitendra Kotamraju
+ * @author Kin-man Chung
  */
+
 class JsonArrayBuilderImpl implements JsonArrayBuilder {
     private ArrayList<JsonValue> valueList;
@@ -65,4 +69,17 @@
     }
 
+    JsonArrayBuilderImpl(JsonArray array, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
+        valueList = new ArrayList<>();
+        valueList.addAll(array);
+    }
+
+    JsonArrayBuilderImpl(Collection<?> collection, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
+        valueList = new ArrayList<>();
+        populate(collection);
+    }
+
+    @Override
     public JsonArrayBuilder add(JsonValue value) {
         validateValue(value);
@@ -71,4 +88,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(String value) {
         validateValue(value);
@@ -77,4 +95,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(BigDecimal value) {
         validateValue(value);
@@ -83,4 +102,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(BigInteger value) {
         validateValue(value);
@@ -89,4 +109,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(int value) {
         addValueList(JsonNumberImpl.getJsonNumber(value));
@@ -94,4 +115,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(long value) {
         addValueList(JsonNumberImpl.getJsonNumber(value));
@@ -99,4 +121,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(double value) {
         addValueList(JsonNumberImpl.getJsonNumber(value));
@@ -104,4 +127,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(boolean value) {
         addValueList(value ? JsonValue.TRUE : JsonValue.FALSE);
@@ -109,4 +133,5 @@
     }
 
+    @Override
     public JsonArrayBuilder addNull() {
         addValueList(JsonValue.NULL);
@@ -114,4 +139,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(JsonObjectBuilder builder) {
         if (builder == null) {
@@ -122,4 +148,5 @@
     }
 
+    @Override
     public JsonArrayBuilder add(JsonArrayBuilder builder) {
         if (builder == null) {
@@ -130,4 +157,178 @@
     }
 
+    @Override
+    public JsonArrayBuilder addAll(JsonArrayBuilder builder) {
+        if (builder == null) {
+            throw new NullPointerException(JsonMessages.ARRBUILDER_ARRAY_BUILDER_NULL());
+        }
+        if (valueList == null) {
+            valueList = new ArrayList<>();
+        }
+        valueList.addAll(builder.build());
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, JsonValue value) {
+        validateValue(value);
+        addValueList(index, value);
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, String value) {
+        validateValue(value);
+        addValueList(index, new JsonStringImpl(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, BigDecimal value) {
+        validateValue(value);
+        addValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, BigInteger value) {
+        validateValue(value);
+        addValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, int value) {
+        addValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, long value) {
+        addValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, double value) {
+        addValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, boolean value) {
+        addValueList(index, value ? JsonValue.TRUE : JsonValue.FALSE);
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder addNull(int index) {
+        addValueList(index, JsonValue.NULL);
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, JsonObjectBuilder builder) {
+        if (builder == null) {
+            throw new NullPointerException(JsonMessages.ARRBUILDER_OBJECT_BUILDER_NULL());
+        }
+        addValueList(index, builder.build());
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder add(int index, JsonArrayBuilder builder) {
+        if (builder == null) {
+            throw new NullPointerException(JsonMessages.ARRBUILDER_OBJECT_BUILDER_NULL());
+        }
+        addValueList(index, builder.build());
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, JsonValue value) {
+        validateValue(value);
+        setValueList(index, value);
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, String value) {
+        validateValue(value);
+        setValueList(index, new JsonStringImpl(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, BigDecimal value) {
+        validateValue(value);
+        setValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, BigInteger value) {
+        validateValue(value);
+        setValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, int value) {
+        setValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, long value) {
+        setValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, double value) {
+        setValueList(index, JsonNumberImpl.getJsonNumber(value));
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, boolean value) {
+        setValueList(index, value ? JsonValue.TRUE : JsonValue.FALSE);
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder setNull(int index) {
+        setValueList(index, JsonValue.NULL);
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, JsonObjectBuilder builder) {
+        if (builder == null) {
+            throw new NullPointerException(JsonMessages.ARRBUILDER_OBJECT_BUILDER_NULL());
+        }
+        setValueList(index, builder.build());
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder set(int index, JsonArrayBuilder builder) {
+        if (builder == null) {
+            throw new NullPointerException(JsonMessages.ARRBUILDER_OBJECT_BUILDER_NULL());
+        }
+        setValueList(index, builder.build());
+        return this;
+    }
+
+    @Override
+    public JsonArrayBuilder remove(int index) {
+        if (valueList == null) {
+            throw new IndexOutOfBoundsException(JsonMessages.ARRBUILDER_VALUELIST_NULL(index, 0));
+        }
+        valueList.remove(index);
+        return this;
+    }
+
+    @Override
     public JsonArray build() {
         List<JsonValue> snapshot;
@@ -143,9 +344,34 @@
     }
 
+    private void populate(Collection<?> collection) {
+        for (Object value : collection) {
+            if (value != null && value instanceof Optional) {
+                ((Optional<?>) value).ifPresent(v ->
+                        this.valueList.add(MapUtil.handle(v, bufferPool)));
+            } else {
+                this.valueList.add(MapUtil.handle(value, bufferPool));
+            }
+        }
+    }
+
     private void addValueList(JsonValue value) {
         if (valueList == null) {
-            valueList = new ArrayList<JsonValue>();
+            valueList = new ArrayList<>();
         }
         valueList.add(value);
+    }
+
+    private void addValueList(int index, JsonValue value) {
+        if (valueList == null) {
+            valueList = new ArrayList<>();
+        }
+        valueList.add(index, value);
+    }
+
+    private void setValueList(int index, JsonValue value) {
+        if (valueList == null) {
+            throw new IndexOutOfBoundsException(JsonMessages.ARRBUILDER_VALUELIST_NULL(index, 0));
+        }
+        valueList.set(index, value);
     }
 
@@ -263,13 +489,15 @@
         public String toString() {
             StringWriter sw = new StringWriter();
-            JsonWriter jw = new JsonWriterImpl(sw, bufferPool);
-            jw.write(this);
-            jw.close();
+            try (JsonWriter jw = new JsonWriterImpl(sw, bufferPool)) {
+                jw.write(this);
+            }
             return sw.toString();
         }
-    }
-
+
+        @Override
+        public JsonArray asJsonArray() {
+            return this;
+        }
+    }
 }
 
-
-
Index: trunk/src/org/glassfish/json/JsonBuilderFactoryImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonBuilderFactoryImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonBuilderFactoryImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -41,6 +41,9 @@
 package org.glassfish.json;
 
+import java.util.Collection;
 import org.glassfish.json.api.BufferPool;
 
+import javax.json.JsonObject;
+import javax.json.JsonArray;
 import javax.json.JsonArrayBuilder;
 import javax.json.JsonBuilderFactory;
@@ -65,4 +68,14 @@
         return new JsonObjectBuilderImpl(bufferPool);
     }
+ 
+    @Override
+    public JsonObjectBuilder createObjectBuilder(JsonObject object) {
+        return new JsonObjectBuilderImpl(object, bufferPool);
+    }
+
+    @Override
+    public JsonObjectBuilder createObjectBuilder(Map<String, Object> object) {
+        return new JsonObjectBuilderImpl(object, bufferPool);
+    }
 
     @Override
@@ -72,4 +85,14 @@
 
     @Override
+    public JsonArrayBuilder createArrayBuilder(JsonArray array) {
+        return new JsonArrayBuilderImpl(array, bufferPool);
+    }
+
+    @Override
+    public JsonArrayBuilder createArrayBuilder(Collection<?> collection) {
+        return new JsonArrayBuilderImpl(collection, bufferPool);
+    }
+
+    @Override
     public Map<String, ?> getConfigInUse() {
         return config;
Index: trunk/src/org/glassfish/json/JsonGeneratorFactoryImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonGeneratorFactoryImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonGeneratorFactoryImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
Index: trunk/src/org/glassfish/json/JsonGeneratorImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonGeneratorImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonGeneratorImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -50,4 +50,5 @@
 import java.math.BigInteger;
 import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
 import java.util.ArrayDeque;
 import java.util.Deque;
@@ -58,5 +59,4 @@
  */
 class JsonGeneratorImpl implements JsonGenerator {
-    private static final Charset UTF_8 = Charset.forName("UTF-8");
 
     private static final char[] INT_MIN_VALUE_CHARS = "-2147483648".toCharArray();
@@ -101,4 +101,5 @@
         IN_NONE,
         IN_OBJECT,
+        IN_FIELD,
         IN_ARRAY
     }
@@ -107,5 +108,5 @@
     private final Writer writer;
     private Context currentContext = new Context(Scope.IN_NONE);
-    private final Deque<Context> stack = new ArrayDeque<Context>();
+    private final Deque<Context> stack = new ArrayDeque<>();
 
     // Using own buffering mechanism as JDK's BufferedWriter uses synchronized
@@ -122,5 +123,5 @@
 
     JsonGeneratorImpl(OutputStream out, BufferPool bufferPool) {
-        this(out, UTF_8, bufferPool);
+        this(out, StandardCharsets.UTF_8, bufferPool);
     }
 
@@ -170,5 +171,5 @@
         writeComma();
         writeEscapedString(name);
-        writeChar(':');
+        writeColon();
         return this;
     }
@@ -267,8 +268,6 @@
     @Override
     public JsonGenerator write(JsonValue value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
+
         switch (value.getValueType()) {
             case ARRAY:
@@ -295,4 +294,5 @@
                 JsonNumber number = (JsonNumber)value;
                 writeValue(number.toString());
+                popFieldContext();
                 break;
             case TRUE:
@@ -382,22 +382,20 @@
     }
 
+    @Override
     public JsonGenerator write(String value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeComma();
         writeEscapedString(value);
-        return this;
-    }
-
-
+        popFieldContext();
+        return this;
+    }
+
+
+    @Override
     public JsonGenerator write(int value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeComma();
         writeInt(value);
+        popFieldContext();
         return this;
     }
@@ -405,9 +403,7 @@
     @Override
     public JsonGenerator write(long value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeValue(String.valueOf(value));
+        popFieldContext();
         return this;
     }
@@ -415,12 +411,10 @@
     @Override
     public JsonGenerator write(double value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         if (Double.isInfinite(value) || Double.isNaN(value)) {
             throw new NumberFormatException(JsonMessages.GENERATOR_DOUBLE_INFINITE_NAN());
         }
         writeValue(String.valueOf(value));
+        popFieldContext();
         return this;
     }
@@ -428,39 +422,48 @@
     @Override
     public JsonGenerator write(BigInteger value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeValue(value.toString());
-        return this;
+        popFieldContext();
+        return this;
+    }
+
+    private void checkContextForValue() {
+        if ((!currentContext.first && currentContext.scope != Scope.IN_ARRAY && currentContext.scope != Scope.IN_FIELD)
+                || (currentContext.first && currentContext.scope == Scope.IN_OBJECT)) {
+            throw new JsonGenerationException(
+                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
+        }
     }
 
     @Override
     public JsonGenerator write(BigDecimal value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeValue(value.toString());
-        return this;
-    }
-
+        popFieldContext();
+
+        return this;
+    }
+
+    private void popFieldContext() {
+        if (currentContext.scope == Scope.IN_FIELD) {
+            currentContext = stack.pop();
+        }
+    }
+
+    @Override
     public JsonGenerator write(boolean value) {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeComma();
         writeString(value ? "true" : "false");
-        return this;
-    }
-
+        popFieldContext();
+        return this;
+    }
+
+    @Override
     public JsonGenerator writeNull() {
-        if (currentContext.scope != Scope.IN_ARRAY) {
-            throw new JsonGenerationException(
-                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
-        }
+        checkContextForValue();
         writeComma();
         writeString("null");
+        popFieldContext();
         return this;
     }
@@ -474,6 +477,19 @@
         writeComma();
         writeEscapedString(name);
-        writeChar(':');
+        writeColon();
         writeString(value);
+    }
+
+    @Override
+    public JsonGenerator writeKey(String name) {
+        if (currentContext.scope != Scope.IN_OBJECT) {
+            throw new JsonGenerationException(
+                    JsonMessages.GENERATOR_ILLEGAL_METHOD(currentContext.scope));
+        }
+        writeName(name);
+        stack.push(currentContext);
+        currentContext = new Context(Scope.IN_FIELD);
+        currentContext.first = false;
+        return this;
     }
 
@@ -485,12 +501,17 @@
         writeChar(currentContext.scope == Scope.IN_ARRAY ? ']' : '}');
         currentContext = stack.pop();
+        popFieldContext();
         return this;
     }
 
     protected void writeComma() {
-        if (!currentContext.first) {
+        if (!currentContext.first && currentContext.scope != Scope.IN_FIELD) {
             writeChar(',');
         }
         currentContext.first = false;
+    }
+
+    protected void writeColon() {
+        writeChar(':');
     }
 
@@ -505,4 +526,5 @@
     }
 
+    @Override
     public void close() {
         if (currentContext.scope != Scope.IN_NONE || currentContext.first) {
Index: trunk/src/org/glassfish/json/JsonLocationImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonLocationImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonLocationImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -74,4 +74,5 @@
     }
 
+    @Override
     public String toString() {
         return "(line no="+lineNo+", column no="+columnNo+", offset="+ offset +")";
Index: trunk/src/org/glassfish/json/JsonMergePatchImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonMergePatchImpl.java	(revision 13231)
+++ trunk/src/org/glassfish/json/JsonMergePatchImpl.java	(revision 13231)
@@ -0,0 +1,142 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import javax.json.Json;
+import javax.json.JsonMergePatch;
+import javax.json.JsonObject;
+import javax.json.JsonObjectBuilder;
+import javax.json.JsonValue;
+
+/**
+ * This class is an implementation of a JSON Merge Patch as specified in
+ * <a href="http://tools.ietf.org/html/rfc7396">RFC 7396</a>.
+ *
+ * @since 1.1
+ */
+
+public final class JsonMergePatchImpl implements JsonMergePatch {
+
+    private JsonValue patch;
+
+    public JsonMergePatchImpl(JsonValue patch) {
+        this.patch = patch;
+    }
+
+    @Override
+    public JsonValue apply(JsonValue target) {
+        return mergePatch(target, patch);
+    }
+
+    @Override
+    public JsonValue toJsonValue() {
+        return patch;
+    }
+    /**
+     * Applies the specified patch to the specified target.
+     * The target is not modified by the patch.
+     *
+     * @param target the {@code JsonValue} to apply the patch operations
+     * @param patch the patch
+     * @return the {@code JsonValue} as the result of applying the patch
+     *    operations on the target.
+     */
+    private static JsonValue mergePatch(JsonValue target, JsonValue patch) {
+
+        if (patch.getValueType() != JsonValue.ValueType.OBJECT) {
+            return patch;
+        }
+        if (target.getValueType() != JsonValue.ValueType.OBJECT) {
+            target = JsonValue.EMPTY_JSON_OBJECT;
+        }
+        JsonObject targetJsonObject = target.asJsonObject();
+        JsonObjectBuilder builder =
+            Json.createObjectBuilder(targetJsonObject);
+        patch.asJsonObject().forEach((key, value) -> {
+            if (value == JsonValue.NULL) {
+                if (targetJsonObject.containsKey(key)) {
+                    builder.remove(key);
+                }
+            } else if (targetJsonObject.containsKey(key)) {
+                builder.add(key, mergePatch(targetJsonObject.get(key), value));
+            } else {
+                builder.add(key, mergePatch(JsonValue.EMPTY_JSON_OBJECT, value));
+            }
+        });
+        return builder.build();
+    }
+
+    /**
+     * Generate a JSON Merge Patch from the source and target {@code JsonValue}.
+     * @param source the source
+     * @param target the target
+     * @return a JSON Patch which when applied to the source, yields the target
+     */
+    static JsonValue diff(JsonValue source, JsonValue target) {
+        if (source.getValueType() != JsonValue.ValueType.OBJECT ||
+                target.getValueType() != JsonValue.ValueType.OBJECT) {
+            return target;
+        }
+        JsonObject s = (JsonObject) source;
+        JsonObject t = (JsonObject) target;
+        JsonObjectBuilder builder = Json.createObjectBuilder();
+        // First find members to be replaced or removed
+        s.forEach((key, value) -> {
+            if (t.containsKey(key)) {
+                // key present in both.
+                if (! value.equals(t.get(key))) {
+                    // If the values are equal, nop, else get diff for the values
+                    builder.add(key, diff(value, t.get(key)));
+                }
+            } else {
+                builder.addNull(key);
+            }
+        });
+        // Then find members to be added
+        t.forEach((key, value) -> {
+            if (! s.containsKey(key))
+                builder.add(key, value);
+        });
+        return builder.build();
+    }
+
+}
+
Index: trunk/src/org/glassfish/json/JsonMessages.java
===================================================================
--- trunk/src/org/glassfish/json/JsonMessages.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonMessages.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -46,4 +46,6 @@
 import java.text.MessageFormat;
 import java.util.ResourceBundle;
+import javax.json.JsonObject;
+import javax.json.JsonValue;
 
 /**
@@ -56,4 +58,9 @@
             ResourceBundle.getBundle("org.glassfish.json.messages");
 
+    // global/shared messages
+    static String INTERNAL_ERROR() {
+        return localize("internal.error");
+    }
+
     // tokenizer messages
     static String TOKENIZER_UNEXPECTED_CHAR(int unexpected, JsonLocation location) {
@@ -91,4 +98,20 @@
     }
 
+    static String PARSER_GETARRAY_ERR(JsonParser.Event event) {
+        return localize("parser.getArray.err", event);
+    }
+
+    static String PARSER_GETOBJECT_ERR(JsonParser.Event event) {
+        return localize("parser.getObject.err", event);
+    }
+
+    static String PARSER_GETVALUE_ERR(JsonParser.Event event) {
+        return localize("parser.getValue.err", event);
+    }
+
+    static String PARSER_GETVALUESTREAM_ERR() {
+        return localize("parser.getValueStream.err");
+    }
+
     static String PARSER_EXPECTED_EOF(JsonTokenizer.JsonToken token) {
         return localize("parser.expected.eof", token);
@@ -103,4 +126,19 @@
     }
 
+    static String PARSER_STATE_ERR(JsonValue.ValueType type) {
+        return localize("parser.state.err", type);
+    }
+
+    static String PARSER_SCOPE_ERR(JsonValue value) {
+        return localize("parser.scope.err", value);
+    }
+
+    static String PARSER_INPUT_ENC_DETECT_FAILED() {
+        return localize("parser.input.enc.detect.failed");
+    }
+
+    static String PARSER_INPUT_ENC_DETECT_IOERR() {
+        return localize("parser.input.enc.detect.ioerr");
+    }
 
     // generator messages
@@ -140,5 +178,4 @@
     }
 
-
     // reader messages
     static String READER_READ_ALREADY_CALLED() {
@@ -146,12 +183,4 @@
     }
 
-    static String READER_EXPECTED_ARRAY_GOT_OBJECT() {
-        return localize("reader.expected.array.got.object");
-    }
-
-    static String READER_EXPECTED_OBJECT_GOT_ARRAY() {
-        return localize("reader.expected.object.got.array");
-    }
-
 
     // obj builder messages
@@ -184,4 +213,71 @@
     static String ARRBUILDER_ARRAY_BUILDER_NULL() {
         return localize("arrbuilder.array.builder.null");
+    }
+
+    static String ARRBUILDER_VALUELIST_NULL(int index, int size) {
+        return localize("arrbuilder.valuelist.null", index, size);
+    }
+
+    // json pointer messages
+    static String POINTER_FORMAT_INVALID() {
+        return localize("pointer.format.invalid");
+    }
+
+    static String POINTER_MAPPING_MISSING(JsonObject object, String key) {
+        return localize("pointer.mapping.missing", object, key);
+    }
+
+    static String POINTER_REFERENCE_INVALID(JsonValue.ValueType type) {
+        return localize("pointer.reference.invalid", type.name());
+    }
+
+    static String POINTER_ARRAY_INDEX_ERR(String token) {
+        return localize("pointer.array.index.err", token);
+    }
+
+    static String POINTER_ARRAY_INDEX_ILLEGAL(String token) {
+        return localize("pointer.array.index.illegal", token);
+    }
+
+    // nodereference messages
+    static String NODEREF_VALUE_ADD_ERR() {
+        return localize("noderef.value.add.err");
+    }
+
+    static String NODEREF_VALUE_CANNOT_REMOVE() {
+        return localize("noderef.value.cannot.remove");
+    }
+
+    static String NODEREF_OBJECT_MISSING(String key) {
+        return localize("noderef.object.missing", key);
+    }
+
+    static String NODEREF_ARRAY_INDEX_ERR(int index, int size) {
+        return localize("noderef.array.index.err", index, size);
+    }
+
+    // json patch messages
+    static String PATCH_MUST_BE_ARRAY() {
+        return localize("patch.must.be.array");
+    }
+
+    static String PATCH_MOVE_PROPER_PREFIX(String from, String path) {
+        return localize("patch.move.proper.prefix", from, path);
+    }
+
+    static String PATCH_MOVE_TARGET_NULL(String from) {
+        return localize("patch.move.target.null", from);
+    }
+
+    static String PATCH_TEST_FAILED(String path, String value) {
+        return localize("patch.test.failed", path, value);
+    }
+
+    static String PATCH_ILLEGAL_OPERATION(String operation) {
+        return localize("patch.illegal.operation", operation);
+    }
+
+    static String PATCH_MEMBER_MISSING(String operation, String member) {
+        return localize("patch.member.missing", operation, member);
     }
 
Index: trunk/src/org/glassfish/json/JsonNumberImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonNumberImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonNumberImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -126,4 +126,9 @@
 
         @Override
+        public Number numberValue() {
+            return num;
+        }
+
+        @Override
         public String toString() {
             return Integer.toString(num);
@@ -143,4 +148,14 @@
         public boolean isIntegral() {
             return true;
+        }
+
+        @Override
+        public int intValue() {
+            return (int) num;
+        }
+
+        @Override
+        public int intValueExact() {
+            return Math.toIntExact(num);
         }
 
@@ -172,4 +187,9 @@
 
         @Override
+        public Number numberValue() {
+            return num;
+        }
+
+        @Override
         public String toString() {
             return Long.toString(num);
@@ -191,4 +211,9 @@
         }
 
+        @Override
+        public Number numberValue() {
+            return bigDecimalValue();
+        }
+
     }
 
@@ -245,4 +270,7 @@
     @Override
     public boolean equals(Object obj) {
+        if (this == obj){
+            return true;
+        }
         if (!(obj instanceof JsonNumber)) {
             return false;
Index: trunk/src/org/glassfish/json/JsonObjectBuilderImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonObjectBuilderImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonObjectBuilderImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -51,9 +51,11 @@
 
 /**
- * JsonObjectBuilder impl
+ * JsonObjectBuilder implementation
  *
  * @author Jitendra Kotamraju
+ * @author Kin-man Chung
  */
 class JsonObjectBuilderImpl implements JsonObjectBuilder {
+
     private Map<String, JsonValue> valueMap;
     private final BufferPool bufferPool;
@@ -63,4 +65,17 @@
     }
 
+    JsonObjectBuilderImpl(JsonObject object, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
+        valueMap = new LinkedHashMap<>();
+        valueMap.putAll(object);
+    }
+
+    JsonObjectBuilderImpl(Map<String, Object> map, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
+        valueMap = new LinkedHashMap<>();
+        populate(map);
+    }
+
+    @Override
     public JsonObjectBuilder add(String name, JsonValue value) {
         validateName(name);
@@ -70,4 +85,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, String value) {
         validateName(name);
@@ -77,4 +93,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, BigInteger value) {
         validateName(name);
@@ -84,4 +101,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, BigDecimal value) {
         validateName(name);
@@ -91,4 +109,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, int value) {
         validateName(name);
@@ -97,4 +116,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, long value) {
         validateName(name);
@@ -103,4 +123,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, double value) {
         validateName(name);
@@ -109,4 +130,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, boolean value) {
         validateName(name);
@@ -115,4 +137,5 @@
     }
 
+    @Override
     public JsonObjectBuilder addNull(String name) {
         validateName(name);
@@ -121,4 +144,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, JsonObjectBuilder builder) {
         validateName(name);
@@ -130,4 +154,5 @@
     }
 
+    @Override
     public JsonObjectBuilder add(String name, JsonArrayBuilder builder) {
         validateName(name);
@@ -139,4 +164,24 @@
     }
 
+    @Override
+    public JsonObjectBuilder addAll(JsonObjectBuilder builder) {
+        if (builder == null) {
+            throw new NullPointerException(JsonMessages.OBJBUILDER_OBJECT_BUILDER_NULL());
+        }
+        if (valueMap == null) {
+            this.valueMap = new LinkedHashMap<>();
+        }
+        this.valueMap.putAll(builder.build());
+        return this;
+    }
+
+    @Override
+    public JsonObjectBuilder remove(String name) {
+        validateName(name);
+        this.valueMap.remove(name);
+        return this;
+    }
+
+    @Override
     public JsonObject build() {
         Map<String, JsonValue> snapshot = (valueMap == null)
@@ -147,7 +192,20 @@
     }
 
+    private void populate(Map<String, Object> map) {
+        final Set<String> fields = map.keySet();
+        for (String field : fields) {
+            Object value = map.get(field);
+            if (value != null && value instanceof Optional) {
+                ((Optional<?>) value).ifPresent(v ->
+                        this.valueMap.put(field, MapUtil.handle(v, bufferPool)));
+            } else {
+                this.valueMap.put(field, MapUtil.handle(value, bufferPool));
+            }
+        }
+    }
+
     private void putValueMap(String name, JsonValue value) {
         if (valueMap == null) {
-            this.valueMap = new LinkedHashMap<String, JsonValue>();
+            this.valueMap = new LinkedHashMap<>();
         }
         valueMap.put(name, value);
@@ -264,9 +322,29 @@
         public String toString() {
             StringWriter sw = new StringWriter();
-            JsonWriter jw = new JsonWriterImpl(sw, bufferPool);
-            jw.write(this);
-            jw.close();
+            try (JsonWriter jw = new JsonWriterImpl(sw, bufferPool)) {
+                jw.write(this);
+            }
             return sw.toString();
         }
+
+        @Override
+        public JsonObject asJsonObject() {
+            return this;
+        }
+
+        @Override
+        public int size() {
+            return valueMap.size();
+        }
+
+        @Override
+        public JsonValue get(Object key) {
+            return valueMap.get(key);
+        }
+
+        @Override
+        public boolean containsKey(Object key) {
+            return valueMap.containsKey(key);
+        }
     }
 
Index: trunk/src/org/glassfish/json/JsonParserFactoryImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonParserFactoryImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonParserFactoryImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
Index: trunk/src/org/glassfish/json/JsonParserImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonParserImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonParserImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -41,12 +41,29 @@
 package org.glassfish.json;
 
-import javax.json.*;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.math.BigDecimal;
+import java.nio.charset.Charset;
+import java.util.AbstractMap;
+import java.util.Map;
+import java.util.NoSuchElementException;
+import java.util.Spliterator;
+import java.util.Spliterators;
+import java.util.function.Consumer;
+import java.util.stream.Stream;
+import java.util.stream.StreamSupport;
+
+import javax.json.JsonArray;
+import javax.json.JsonArrayBuilder;
+import javax.json.JsonException;
+import javax.json.JsonObject;
+import javax.json.JsonObjectBuilder;
+import javax.json.JsonValue;
 import javax.json.stream.JsonLocation;
 import javax.json.stream.JsonParser;
+import javax.json.stream.JsonParser.Event;
 import javax.json.stream.JsonParsingException;
-import java.io.*;
-import java.math.BigDecimal;
-import java.nio.charset.Charset;
-import java.util.*;
 
 import org.glassfish.json.JsonTokenizer.JsonToken;
@@ -58,30 +75,32 @@
  *
  * @author Jitendra Kotamraju
+ * @author Kin-man Chung
  */
 public class JsonParserImpl implements JsonParser {
 
+    private final BufferPool bufferPool;
     private Context currentContext = new NoneContext();
     private Event currentEvent;
 
     private final Stack stack = new Stack();
-    private final StateIterator stateIterator;
     private final JsonTokenizer tokenizer;
 
     public JsonParserImpl(Reader reader, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
         tokenizer = new JsonTokenizer(reader, bufferPool);
-        stateIterator = new StateIterator();
     }
 
     public JsonParserImpl(InputStream in, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
         UnicodeDetectingInputStream uin = new UnicodeDetectingInputStream(in);
         tokenizer = new JsonTokenizer(new InputStreamReader(uin, uin.getCharset()), bufferPool);
-        stateIterator = new StateIterator();
     }
 
     public JsonParserImpl(InputStream in, Charset encoding, BufferPool bufferPool) {
+        this.bufferPool = bufferPool;
         tokenizer = new JsonTokenizer(new InputStreamReader(in, encoding), bufferPool);
-        stateIterator = new StateIterator();
-    }
-
+    }
+
+    @Override
     public String getString() {
         if (currentEvent == Event.KEY_NAME || currentEvent == Event.VALUE_STRING
@@ -115,4 +134,8 @@
     }
 
+    boolean isDefinitelyLong() {
+    	return tokenizer.isDefinitelyLong();
+    }
+
     @Override
     public long getLong() {
@@ -121,5 +144,5 @@
                     JsonMessages.PARSER_GETLONG_ERR(currentEvent));
         }
-        return tokenizer.getBigDecimal().longValue();
+        return tokenizer.getLong();
     }
 
@@ -134,4 +157,190 @@
 
     @Override
+    public JsonArray getArray() {
+        if (currentEvent != Event.START_ARRAY) {
+            throw new IllegalStateException(
+                JsonMessages.PARSER_GETARRAY_ERR(currentEvent));
+        }
+        return getArray(new JsonArrayBuilderImpl(bufferPool));
+    }
+
+    @Override
+    public JsonObject getObject() {
+        if (currentEvent != Event.START_OBJECT) {
+            throw new IllegalStateException(
+                JsonMessages.PARSER_GETOBJECT_ERR(currentEvent));
+        }
+        return getObject(new JsonObjectBuilderImpl(bufferPool));
+    }
+
+    @Override
+    public JsonValue getValue() {
+        switch (currentEvent) {
+            case START_ARRAY:
+                return getArray(new JsonArrayBuilderImpl(bufferPool));
+            case START_OBJECT:
+                return getObject(new JsonObjectBuilderImpl(bufferPool));
+            case KEY_NAME:
+            case VALUE_STRING:
+                return new JsonStringImpl(getString());
+            case VALUE_NUMBER:
+                if (isDefinitelyInt()) {
+                    return JsonNumberImpl.getJsonNumber(getInt());
+                } else if (isDefinitelyLong()) {
+                    return JsonNumberImpl.getJsonNumber(getLong());
+                }
+                return JsonNumberImpl.getJsonNumber(getBigDecimal());
+            case VALUE_TRUE:
+                return JsonValue.TRUE;
+            case VALUE_FALSE:
+                return JsonValue.FALSE;
+            case VALUE_NULL:
+                return JsonValue.NULL;
+            case END_ARRAY:
+            case END_OBJECT:
+            default:
+            	throw new IllegalStateException(JsonMessages.PARSER_GETVALUE_ERR(currentEvent));
+        }
+    }
+
+    @Override
+    public Stream<JsonValue> getArrayStream() {
+        if (currentEvent != Event.START_ARRAY) {
+            throw new IllegalStateException(
+                JsonMessages.PARSER_GETARRAY_ERR(currentEvent));
+        }
+        Spliterator<JsonValue> spliterator =
+                new Spliterators.AbstractSpliterator<JsonValue>(Long.MAX_VALUE, Spliterator.ORDERED) {
+            @Override
+            public Spliterator<JsonValue> trySplit() {
+                return null;
+            }
+            @Override
+            public boolean tryAdvance(Consumer<? super JsonValue> action) {
+                if (action == null) {
+                    throw new NullPointerException();
+                }
+                if (! hasNext()) {
+                    return false;
+                }
+                if (next() == JsonParser.Event.END_ARRAY) {
+                    return false;
+                }
+                action.accept(getValue());
+                return true;
+            }
+        };
+        return StreamSupport.stream(spliterator, false);
+    }
+
+    @Override
+    public Stream<Map.Entry<String, JsonValue>> getObjectStream() {
+        if (currentEvent != Event.START_OBJECT) {
+            throw new IllegalStateException(
+                JsonMessages.PARSER_GETOBJECT_ERR(currentEvent));
+        }
+        Spliterator<Map.Entry<String, JsonValue>> spliterator =
+                new Spliterators.AbstractSpliterator<Map.Entry<String, JsonValue>>(Long.MAX_VALUE, Spliterator.ORDERED) {
+            @Override
+            public Spliterator<Map.Entry<String,JsonValue>> trySplit() {
+                return null;
+            }
+            @Override
+            public boolean tryAdvance(Consumer<? super Map.Entry<String, JsonValue>> action) {
+                if (action == null) {
+                    throw new NullPointerException();
+                }
+                if (! hasNext()) {
+                    return false;
+                }
+                JsonParser.Event e = next();
+                if (e == JsonParser.Event.END_OBJECT) {
+                    return false;
+                }
+                if (e != JsonParser.Event.KEY_NAME) {
+                    throw new JsonException(JsonMessages.INTERNAL_ERROR());
+                }
+                String key = getString();
+                if (! hasNext()) {
+                    throw new JsonException(JsonMessages.INTERNAL_ERROR());
+                }
+                next();
+                JsonValue value = getValue();
+                action.accept(new AbstractMap.SimpleImmutableEntry<>(key, value));
+                return true;
+            }
+        };
+        return StreamSupport.stream(spliterator, false);
+    }
+
+    @Override
+    public Stream<JsonValue> getValueStream() {
+        if (! (currentContext instanceof NoneContext)) {
+            throw new IllegalStateException(
+                JsonMessages.PARSER_GETVALUESTREAM_ERR());
+        }
+        Spliterator<JsonValue> spliterator =
+                new Spliterators.AbstractSpliterator<JsonValue>(Long.MAX_VALUE, Spliterator.ORDERED) {
+            @Override
+            public Spliterator<JsonValue> trySplit() {
+                return null;
+            }
+            @Override
+            public boolean tryAdvance(Consumer<? super JsonValue> action) {
+                if (action == null) {
+                    throw new NullPointerException();
+                }
+                if (! hasNext()) {
+                    return false;
+                }
+                next();
+                action.accept(getValue());
+                return true;
+            }
+        };
+        return StreamSupport.stream(spliterator, false);
+    }
+
+    @Override
+    public void skipArray() {
+        if (currentEvent == Event.START_ARRAY) {
+            currentContext.skip();
+            currentContext = stack.pop();
+        }
+    }
+
+    @Override
+    public void skipObject() {
+        if (currentEvent == Event.START_OBJECT) {
+            currentContext.skip();
+            currentContext = stack.pop();
+        }
+    }
+
+    private JsonArray getArray(JsonArrayBuilder builder) {
+        while(hasNext()) {
+            JsonParser.Event e = next();
+            if (e == JsonParser.Event.END_ARRAY) {
+                return builder.build();
+            }
+            builder.add(getValue());
+        }
+        throw parsingException(JsonToken.EOF, "[CURLYOPEN, SQUAREOPEN, STRING, NUMBER, TRUE, FALSE, NULL, SQUARECLOSE]");
+    }
+
+    private JsonObject getObject(JsonObjectBuilder builder) {
+        while(hasNext()) {
+            JsonParser.Event e = next();
+            if (e == JsonParser.Event.END_OBJECT) {
+                return builder.build();
+            }
+            String key = getString();
+            next();
+            builder.add(key, getValue());
+        }
+        throw parsingException(JsonToken.EOF, "[STRING, CURLYCLOSE]");
+    }
+
+    @Override
     public JsonLocation getLocation() {
         return tokenizer.getLocation();
@@ -142,41 +351,18 @@
     }
 
+    @Override
     public boolean hasNext() {
-        return stateIterator.hasNext();
-    }
-
+        return tokenizer.hasNextToken();
+    }
+
+    @Override
     public Event next() {
-        return stateIterator.next();
-    }
-
-    private class StateIterator implements  Iterator<JsonParser.Event> {
-
-        @Override
-        public boolean hasNext() {
-            if (stack.isEmpty() && (currentEvent == Event.END_ARRAY || currentEvent == Event.END_OBJECT)) {
-                JsonToken token = tokenizer.nextToken();
-                if (token != JsonToken.EOF) {
-                    throw new JsonParsingException(JsonMessages.PARSER_EXPECTED_EOF(token),
-                            getLastCharLocation());
-                }
-                return false;
-            }
-            return true;
-        }
-
-        @Override
-        public JsonParser.Event next() {
-            if (!hasNext()) {
-                throw new NoSuchElementException();
-            }
-            return currentEvent = currentContext.getNextEvent();
-        }
-
-        @Override
-        public void remove() {
-            throw new UnsupportedOperationException();
-        }
-    }
-
+        if (!hasNext()) {
+            throw new NoSuchElementException();
+        }
+        return currentEvent = currentContext.getNextEvent();
+    }
+
+    @Override
     public void close() {
         try {
@@ -206,4 +392,8 @@
         }
 
+        private Context peek() {
+            return head;
+        }
+
         private boolean isEmpty() {
             return head == null;
@@ -214,4 +404,5 @@
         Context next;
         abstract Event getNextEvent();
+        abstract void skip();
     }
 
@@ -219,5 +410,5 @@
         @Override
         public Event getNextEvent() {
-            // Handle 1. {     2. [
+            // Handle 1. {   2. [   3. value
             JsonToken token = tokenizer.nextToken();
             if (token == JsonToken.CURLYOPEN) {
@@ -229,6 +420,13 @@
                 currentContext = new ArrayContext();
                 return Event.START_ARRAY;
-            }
-            throw parsingException(token, "[CURLYOPEN, SQUAREOPEN]");
+            } else if (token.isValue()) {
+                return token.getEvent();
+            }
+            throw parsingException(token, "[CURLYOPEN, SQUAREOPEN, STRING, NUMBER, TRUE, FALSE, NULL]");
+        }
+
+        @Override
+        void skip() {
+            // no-op
         }
     }
@@ -293,4 +491,21 @@
         }
 
+        @Override
+        void skip() {
+            JsonToken token;
+            int depth = 1;
+            do {
+                token = tokenizer.nextToken();
+                switch (token) {
+                    case CURLYCLOSE:
+                        depth--;
+                        break;
+                    case CURLYOPEN:
+                        depth++;
+                        break;
+                }
+            } while (!(token == JsonToken.CURLYCLOSE && depth == 0));
+        }
+
     }
 
@@ -328,4 +543,20 @@
         }
 
+        @Override
+        void skip() {
+            JsonToken token;
+            int depth = 1;
+            do {
+                token = tokenizer.nextToken();
+                switch (token) {
+                    case SQUARECLOSE:
+                        depth--;
+                        break;
+                    case SQUAREOPEN:
+                        depth++;
+                        break;
+                }
+            } while (!(token == JsonToken.SQUARECLOSE && depth == 0));
+        }
     }
 
Index: trunk/src/org/glassfish/json/JsonPatchBuilderImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonPatchBuilderImpl.java	(revision 13231)
+++ trunk/src/org/glassfish/json/JsonPatchBuilderImpl.java	(revision 13231)
@@ -0,0 +1,362 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import javax.json.Json;
+import javax.json.JsonArray;
+import javax.json.JsonArrayBuilder;
+import javax.json.JsonException;
+import javax.json.JsonPatch;
+import javax.json.JsonPatch.Operation;
+import javax.json.JsonPatchBuilder;
+import javax.json.JsonStructure;
+import javax.json.JsonValue;
+
+/**
+ * A builder for constructing a JSON Patch by adding
+ * JSON Patch operations incrementally.
+ * <p>
+ * The following illustrates the approach.
+ * <pre>
+ *   JsonPatchBuilder builder = Json.createPatchBuilder();
+ *   JsonPatch patch = builder.add("/John/phones/office", "1234-567")
+ *                            .remove("/Amy/age")
+ *                            .build();
+ * </pre>
+ * The result is equivalent to the following JSON Patch.
+ * <pre>
+ * [
+ *    {"op" = "add", "path" = "/John/phones/office", "value" = "1234-567"},
+ *    {"op" = "remove", "path" = "/Amy/age"}
+ * ] </pre>
+ *
+ * @since 1.1
+ */
+public final class JsonPatchBuilderImpl implements JsonPatchBuilder {
+
+    private final JsonArrayBuilder builder;
+
+    /**
+     * Creates a JsonPatchBuilderImpl, starting with the specified
+     * JSON Patch
+     * @param patch the JSON Patch
+     */
+    public JsonPatchBuilderImpl(JsonArray patch) {
+        builder = Json.createArrayBuilder(patch);
+    }
+
+    /**
+     * Creates JsonPatchBuilderImpl with empty JSON Patch
+     */
+    public JsonPatchBuilderImpl() {
+        builder = Json.createArrayBuilder();
+    }
+
+    /**
+     * A convenience method for {@code new JsonPatchImpl(build()).apply(target)}.
+     * The target is not modified by the patch.
+     *
+     * @param <T> the target type, must be a subtype of {@link JsonStructure}
+     * @param target the target to apply the patch operations
+     * @return the transformed target after the patch
+     * @throws JsonException if the supplied JSON Patch is malformed or if
+     *    it contains references to non-existing members
+     */
+    public <T extends JsonStructure> T apply(T target) {
+        return build().apply(target);
+    }
+
+    /**
+     * Adds an "add" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder add(String path, JsonValue value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.ADD.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                   );
+        return this;
+    }
+
+    /**
+     * Adds an "add" JSON Patch operation
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder add(String path, String value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.ADD.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                   );
+        return this;
+    }
+
+    /**
+     * Adds an "add" JSON Patch operation
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder add(String path, int value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.ADD.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds an "add" JSON Patch operation
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder add(String path, boolean value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.ADD.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                   );
+        return this;
+    }
+
+    /**
+     * Adds a "remove" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder remove(String path) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.REMOVE.operationName())
+                           .add("path", path)
+                    );
+        return this;
+    }
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder replace(String path, JsonValue value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.REPLACE.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder replace(String path, String value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.REPLACE.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder replace(String path, int value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.REPLACE.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "replace" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder replace(String path, boolean value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.REPLACE.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "move" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param from the "from" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder move(String path, String from) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.MOVE.operationName())
+                           .add("path", path)
+                           .add("from", from)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "copy" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param from the "from" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder copy(String path, String from) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.COPY.operationName())
+                           .add("path", path)
+                           .add("from", from)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder test(String path, JsonValue value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.TEST.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder test(String path, String value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.TEST.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder test(String path, int value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.TEST.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Adds a "test" JSON Patch operation.
+     * @param path the "path" member of the operation
+     * @param value the "value" member of the operation
+     * @return this JsonPatchBuilder
+     */
+    @Override
+    public JsonPatchBuilder test(String path, boolean value) {
+        builder.add(Json.createObjectBuilder()
+                           .add("op", Operation.TEST.operationName())
+                           .add("path", path)
+                           .add("value", value)
+                  );
+        return this;
+    }
+
+    /**
+     * Returns the patch operations in a JsonArray
+     * @return the patch operations in a JsonArray
+     */
+    public JsonArray buildAsJsonArray() {
+        return builder.build();
+    }
+
+    /**
+     * Returns the patch operation in a JsonPatch
+     * @return the patch operation in a JsonPatch
+     */
+    @Override
+    public JsonPatch build() {
+        return new JsonPatchImpl(buildAsJsonArray());
+    }
+}
+
Index: trunk/src/org/glassfish/json/JsonPatchImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonPatchImpl.java	(revision 13231)
+++ trunk/src/org/glassfish/json/JsonPatchImpl.java	(revision 13231)
@@ -0,0 +1,321 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import javax.json.*;
+import javax.json.JsonValue.ValueType;
+
+/**
+ * This class is an immutable representation of a JSON Patch as specified in
+ * <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>.
+ * <p>A {@code JsonPatch} can be instantiated with {@link Json#createPatch(JsonArray)}
+ * by specifying the patch operations in a JSON Patch. Alternately, it
+ * can also be constructed with a {@link JsonPatchBuilder}.
+ * </p>
+ * The following illustrates both approaches.
+ * <p>1. Construct a JsonPatch with a JSON Patch.
+ * <pre>{@code
+ *   JsonArray contacts = ... // The target to be patched
+ *   JsonArray patch = ...  ; // JSON Patch
+ *   JsonPatch jsonpatch = Json.createPatch(patch);
+ *   JsonArray result = jsonpatch.apply(contacts);
+ * } </pre>
+ * 2. Construct a JsonPatch with JsonPatchBuilder.
+ * <pre>{@code
+ *   JsonPatchBuilder builder = Json.createPatchBuilder();
+ *   JsonArray result = builder.add("/John/phones/office", "1234-567")
+ *                             .remove("/Amy/age")
+ *                             .build()
+ *                             .apply(contacts);
+ * } </pre>
+ *
+ * @since 1.1
+ */
+public class JsonPatchImpl implements JsonPatch {
+
+    private final JsonArray patch;
+
+    /**
+     * Constructs a JsonPatchImpl
+     * @param patch the JSON Patch
+     */
+    public JsonPatchImpl(JsonArray patch) {
+        this.patch = patch;
+    }
+
+    /**
+     * Compares this {@code JsonPatchImpl} with another object.
+     * @param obj the object to compare this {@code JsonPatchImpl} against
+     * @return true if the given object is a {@code JsonPatchImpl} with the same
+     * reference tokens as this one, false otherwise.
+     */
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj)
+            return true;
+        if (obj == null || obj.getClass() != JsonPatchImpl.class)
+            return false;
+        return patch.equals(((JsonPatchImpl)obj).patch);
+    }
+
+    /**
+     * Returns the hash code value for this {@code JsonPatchImpl}.
+     *
+     * @return the hash code value for this {@code JsonPatchImpl} object
+     */
+    @Override
+    public int hashCode() {
+        return patch.hashCode();
+    }
+
+    /**
+     * Returns the JSON Patch text
+     * @return the JSON Patch text
+     */
+    @Override
+    public String toString() {
+        return patch.toString();
+    }
+
+    /**
+     * Applies the patch operations to the specified {@code target}.
+     * The target is not modified by the patch.
+     *
+     * @param target the target to apply the patch operations
+     * @return the transformed target after the patch
+     * @throws JsonException if the supplied JSON Patch is malformed or if
+     *    it contains references to non-existing members
+     */
+    @Override
+    public JsonStructure apply(JsonStructure target) {
+
+        JsonStructure result = target;
+
+        for (JsonValue operation: patch) {
+            if (operation.getValueType() != ValueType.OBJECT) {
+                throw new JsonException(JsonMessages.PATCH_MUST_BE_ARRAY());
+            }
+            result = apply(result, (JsonObject) operation);
+        }
+        return result;
+    }
+
+    @Override
+    public JsonArray toJsonArray() {
+        return patch;
+    }
+
+    /**
+     * Generates a JSON Patch from the source and target {@code JsonStructure}.
+     * The generated JSON Patch need not be unique.
+     * @param source the source
+     * @param target the target, must be the same type as the source
+     * @return a JSON Patch which when applied to the source, yields the target
+     */
+    public static JsonArray diff(JsonStructure source, JsonStructure target) {
+        return (new DiffGenerator()).diff(source, target);
+    }
+
+    /**
+     * Applies a JSON Patch operation to the target.
+     * @param target the target to apply the operation
+     * @param operation the JSON Patch operation
+     * @return the target after the patch
+     */
+    private JsonStructure apply(JsonStructure target, JsonObject operation) {
+
+        JsonPointer pointer = getPointer(operation, "path");
+        JsonPointer from;
+        switch (Operation.fromOperationName(operation.getString("op"))) {
+            case ADD:
+                return pointer.add(target, getValue(operation));
+            case REPLACE:
+                return pointer.replace(target, getValue(operation));
+            case REMOVE:
+                return pointer.remove(target);
+            case COPY:
+                from = getPointer(operation, "from");
+                return pointer.add(target, from.getValue(target));
+            case MOVE:
+                // Check if from is a proper prefix of path
+                String dest = operation.getString("path");
+                String src = operation.getString("from");
+                if (dest.startsWith(src) && src.length() < dest.length()) {
+                    throw new JsonException(JsonMessages.PATCH_MOVE_PROPER_PREFIX(src, dest));
+                }
+                from = getPointer(operation, "from");
+                // Check if 'from' exists in target object
+                if (!from.containsValue(target)) {
+                    throw new JsonException(JsonMessages.PATCH_MOVE_TARGET_NULL(src));
+                }
+                if (pointer.equals(from)) {
+                    // nop
+                    return target;
+                }
+                return pointer.add(from.remove(target), from.getValue(target));
+            case TEST:
+                if (! getValue(operation).equals(pointer.getValue(target))) {
+                    throw new JsonException(JsonMessages.PATCH_TEST_FAILED(operation.getString("path"), getValue(operation).toString()));
+                }
+                return target;
+            default:
+                throw new JsonException(JsonMessages.PATCH_ILLEGAL_OPERATION(operation.getString("op")));
+        }
+    }
+
+    private JsonPointer getPointer(JsonObject operation, String member) {
+        JsonString pointerString = operation.getJsonString(member);
+        if (pointerString == null) {
+            missingMember(operation.getString("op"), member);
+        }
+        return Json.createPointer(pointerString.getString());
+    }
+
+    private JsonValue getValue(JsonObject operation) {
+        JsonValue value = operation.get("value");
+        if (value == null) {
+            missingMember(operation.getString("op"), "value");
+        }
+        return value;
+    }
+
+    private void missingMember(String op, String  member) {
+        throw new JsonException(JsonMessages.PATCH_MEMBER_MISSING(op, member));
+    }
+
+    static class DiffGenerator {
+        private JsonPatchBuilder builder;
+
+        JsonArray diff(JsonStructure source, JsonStructure target) {
+            builder = Json.createPatchBuilder();
+            diff("", source, target);
+            return builder.build().toJsonArray();
+        }
+
+        private void diff(String path, JsonValue source, JsonValue target) {
+            if (source.equals(target)) {
+                return;
+            }
+            ValueType s = source.getValueType();
+            ValueType t = target.getValueType();
+            if (s == ValueType.OBJECT && t == ValueType.OBJECT) {
+                diffObject(path, (JsonObject) source, (JsonObject) target);
+            } else if (s == ValueType.ARRAY && t == ValueType.ARRAY) {
+                diffArray(path, (JsonArray) source, (JsonArray) target);
+            } else {
+                builder.replace(path, target);
+            }
+        }
+
+        private void diffObject(String path, JsonObject source, JsonObject target) {
+            source.forEach((key, value) -> {
+                if (target.containsKey(key)) {
+                    diff(path + '/' + key, value, target.get(key));
+                } else {
+                    builder.remove(path + '/' + key);
+                }
+            });
+            target.forEach((key, value) -> {
+                if (! source.containsKey(key)) {
+                    builder.add(path + '/' + key, value);
+                }
+            });
+        }
+
+        /*
+         * For array element diff, find the longest common subsequence, per
+         * http://en.wikipedia.org/wiki/Longest_common_subsequence_problem .
+         * We modify the algorithm to generate a replace if possible.
+         */
+        private void diffArray(String path, JsonArray source, JsonArray target) {
+            /* The array c keeps track of length of the subsequence. To avoid
+             * computing the equality of array elements again, we
+             * left shift its value by 1, and use the low order bit to mark
+             * that two items are equal.
+             */
+            int m = source.size();
+            int n = target.size();
+            int [][] c = new int[m+1][n+1];
+            for (int i = 0; i < m+1; i++)
+                c[i][0] = 0;
+            for (int i = 0; i < n+1; i++)
+                c[0][i] = 0;
+            for (int i = 0; i < m; i++) {
+                for (int j = 0; j < n; j++) {
+                    if (source.get(i).equals(target.get(j))) {
+                        c[i+1][j+1] = ((c[i][j]) & ~1) + 3;
+                        // 3 = (1 << 1) | 1;
+                    } else {
+                        c[i+1][j+1] = Math.max(c[i+1][j], c[i][j+1]) & ~1;
+                    }
+                }
+            }
+
+            int i = m;
+            int j = n;
+            while (i > 0 || j > 0) {
+                if (i == 0) {
+                    j--;
+                    builder.add(path + '/' + j, target.get(j));
+                } else if (j == 0) {
+                    i--;
+                    builder.remove(path + '/' + i);
+                } else if ((c[i][j] & 1) == 1) {
+                    i--; j--;
+                } else {
+                    int f = c[i][j-1] >> 1;
+                    int g = c[i-1][j] >> 1;
+                    if (f > g) {
+                        j--;
+                        builder.add(path + '/' + j, target.get(j));
+                    } else if (f < g) {
+                        i--;
+                        builder.remove(path + '/' + i);
+                    } else { // f == g) {
+                       i--; j--;
+                       diff(path + '/' + i, source.get(i), target.get(j));
+                    }
+                }
+            }
+        }
+    }
+}
+
Index: trunk/src/org/glassfish/json/JsonPointerImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonPointerImpl.java	(revision 13231)
+++ trunk/src/org/glassfish/json/JsonPointerImpl.java	(revision 13231)
@@ -0,0 +1,316 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import javax.json.JsonArray;
+import javax.json.JsonException;
+import javax.json.JsonObject;
+import javax.json.JsonPointer;
+import javax.json.JsonStructure;
+import javax.json.JsonValue;
+import java.io.Serializable;
+import java.util.function.BiFunction;
+
+/**
+ * <p>This class is an immutable representation of a JSON Pointer as specified in
+ * <a href="http://tools.ietf.org/html/rfc6901">RFC 6901</a>.
+ * </p>
+ * <p> A JSON Pointer, when applied to a target {@link JsonValue},
+ * defines a reference location in the target.</p>
+ * <p> An empty JSON Pointer string defines a reference to the target itself.</p>
+ * <p> If the JSON Pointer string is non-empty, it must be a sequence
+ * of '/' prefixed tokens, and the target must either be a {@link JsonArray}
+ * or {@link JsonObject}. If the target is a {@code JsonArray}, the pointer
+ * defines a reference to an array element, and the last token specifies the index.
+ * If the target is a {@link JsonObject}, the pointer defines a reference to a
+ * name/value pair, and the last token specifies the name.
+ * </p>
+ * <p> The method {@link #getValue getValue()} returns the referenced value.
+ * The methods {@link #add add()}, {@link #replace replace()},
+ * and {@link #remove remove()} executes the operations specified in
+ * <a href="http://tools.ietf.org/html/rfc6902">RFC 6902</a>. </p>
+ *
+ * @since 1.1
+ */
+
+public final class JsonPointerImpl implements JsonPointer, Serializable {
+
+    private static final long serialVersionUID = -8123110179640843141L;
+    private final String[] tokens;
+    private final String jsonPointer;
+
+    /**
+     * Constructs and initializes a JsonPointerImpl.
+     * @param jsonPointer the JSON Pointer string
+     * @throws NullPointerException if {@code jsonPointer} is {@code null}
+     * @throws JsonException if {@code jsonPointer} is not a valid JSON Pointer
+     */
+    public JsonPointerImpl(String jsonPointer) {
+        this.jsonPointer = jsonPointer;
+        tokens = jsonPointer.split("/", -1);  // keep the trailing blanks
+        if (! "".equals(tokens[0])) {
+            throw new JsonException(JsonMessages.POINTER_FORMAT_INVALID());
+        }
+        for (int i = 1; i < tokens.length; i++) {
+            String token = tokens[i];
+            StringBuilder reftoken = new StringBuilder();
+            for (int j = 0; j < token.length(); j++) {
+                char ch = token.charAt(j);
+                if (ch == '~' && j < token.length() - 1) {
+                    char ch1 = token.charAt(j+1);
+                    if (ch1 == '0') {
+                        ch = '~'; j++;
+                    } else if (ch1 == '1') {
+                        ch = '/'; j++;
+                    }
+                }
+                reftoken.append(ch);
+            }
+            tokens[i] = reftoken.toString();
+        }
+    }
+
+    /**
+     * Compares this {@code JsonPointer} with another object.
+     * @param obj the object to compare this {@code JsonPointer} against
+     * @return true if the given object is a {@code JsonPointer} with the same
+     * reference tokens as this one, false otherwise.
+     */
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj)
+            return true;
+        if (obj == null || obj.getClass() != JsonPointerImpl.class)
+            return false;
+        return jsonPointer.equals(((JsonPointerImpl)obj).jsonPointer);
+    }
+
+    /**
+     * Returns the hash code value for this {@code JsonPointer} object.
+     * The hash code of this object is defined by the hash codes of it's reference tokens.
+     *
+     * @return the hash code value for this {@code JsonPointer} object
+     */
+    @Override
+    public int hashCode() {
+        return jsonPointer.hashCode();
+    }
+
+    /**
+     * Returns {@code true} if there is a value at the referenced location in the specified {@code target}.
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @return {@code true} if this pointer points to a value in a specified {@code target}.
+     */
+    @Override
+    public boolean containsValue(JsonStructure target) {
+        NodeReference[] refs = getReferences(target);
+        return refs[0].contains();
+    }
+
+    /**
+     * Returns the value at the referenced location in the specified {@code target}
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @return the referenced value in the target.
+     * @throws NullPointerException if {@code target} is null
+     * @throws JsonException if the referenced value does not exist
+     */
+    @Override
+    public JsonValue getValue(JsonStructure target) {
+        NodeReference[] refs = getReferences(target);
+        return refs[0].get();
+    }
+
+    /**
+     * Adds or replaces a value at the referenced location in the specified
+     * {@code target} with the specified {@code value}.
+     * <ol>
+     * <li>If the reference is the target (empty JSON Pointer string),
+     * the specified {@code value}, which must be the same type as
+     * specified {@code target}, is returned.</li>
+     * <li>If the reference is an array element, the specified {@code value} is inserted
+     * into the array, at the referenced index. The value currently at that location, and
+     * any subsequent values, are shifted to the right (adds one to the indices).
+     * Index starts with 0. If the reference is specified with a "-", or if the
+     * index is equal to the size of the array, the value is appended to the array.</li>
+     * <li>If the reference is a name/value pair of a {@code JsonObject}, and the
+     * referenced value exists, the value is replaced by the specified {@code value}.
+     * If the value does not exist, a new name/value pair is added to the object.</li>
+     * </ol>
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @param value the value to be added
+     * @return the transformed {@code target} after the value is added.
+     * @throws NullPointerException if {@code target} is {@code null}
+     * @throws JsonException if the reference is an array element and
+     * the index is out of range ({@code index < 0 || index > array size}),
+     * or if the pointer contains references to non-existing objects or arrays.
+     */
+    @Override
+    public JsonStructure add(JsonStructure target, JsonValue value) {
+        return execute(NodeReference::add, target, value);
+    }
+
+    /**
+     * Replaces the value at the referenced location in the specified
+     * {@code target} with the specified {@code value}.
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @param value the value to be stored at the referenced location
+     * @return the transformed {@code target} after the value is replaced.
+     * @throws NullPointerException if {@code target} is {@code null}
+     * @throws JsonException if the referenced value does not exist,
+     *    or if the reference is the target.
+     */
+    @Override
+    public JsonStructure replace(JsonStructure target, JsonValue value) {
+        return execute(NodeReference::replace, target, value);
+    }
+
+    /**
+     * Removes the value at the reference location in the specified {@code target}
+     *
+     * @param target the target referenced by this {@code JsonPointer}
+     * @return the transformed {@code target} after the value is removed.
+     * @throws NullPointerException if {@code target} is {@code null}
+     * @throws JsonException if the referenced value does not exist,
+     *    or if the reference is the target.
+     */
+    @Override
+    public JsonStructure remove(JsonStructure target) {
+        return execute((r,v)->r.remove(), target, null);
+    }
+
+    /**
+     * Executes the operation
+     * @param op a {code BiFunction} used to specify the operation to execute on
+     *    the leaf node of the Json Pointer
+     * @param target the target JsonStructure for this JsonPointer
+     * @param value the JsonValue for add and replace, can be null for getvalue and remove
+     */
+    private JsonStructure execute(BiFunction<NodeReference, JsonValue, JsonStructure> op,
+            JsonStructure target, JsonValue value) {
+
+        NodeReference[] refs = getReferences(target);
+        JsonStructure result = op.apply(refs[0], value);
+        for (int i = 1; i < refs.length; i++) {
+            result = refs[i].replace(result);
+        }
+        return result;
+    }
+
+    /**
+     * Computes the {@code NodeReference}s for each node on the path of
+     * the JSON Pointer, in reverse order, starting from the leaf node
+     */
+    private NodeReference[] getReferences(JsonStructure target) {
+        NodeReference[] references;
+        // First check if this is a reference to a JSON value tree
+        if (tokens.length == 1) {
+            references = new NodeReference[1];
+            references[0] = NodeReference.of(target);
+            return references;
+        }
+
+        references = new NodeReference[tokens.length-1];
+        JsonValue value = target;
+        int s = tokens.length;
+        for (int i = 1; i < s; i++) {
+             // Start with index 1, skipping the "" token
+            switch (value.getValueType()) {
+                case OBJECT:
+                    JsonObject object = (JsonObject) value;
+                    references[s-i-1] = NodeReference.of(object, tokens[i]);
+                    if (i < s-1) {
+                        value = object.get(tokens[i]);
+                        if (value == null) {
+                            // Except for the last name, the mapping must exist
+                            throw new JsonException(JsonMessages.POINTER_MAPPING_MISSING(object, tokens[i]));
+                        }
+                    }
+                    break;
+                case ARRAY:
+                    int index = getIndex(tokens[i]);
+                    JsonArray array = (JsonArray) value;
+                    references[s-i-1] = NodeReference.of(array, index);
+                    if (i < s-1 && index != -1) {
+                        if (index >= array.size()) {
+                            throw new JsonException(JsonMessages.NODEREF_ARRAY_INDEX_ERR(index, array.size()));
+                        }
+                        // The last array index in the path can have index value of -1
+                        // ("-" in the JSON pointer)
+                        value = array.get(index);
+                    }
+                    break;
+                default:
+                    throw new JsonException(JsonMessages.POINTER_REFERENCE_INVALID(value.getValueType()));
+             }
+        }
+        return references;
+    }
+
+    /**
+     * Computes the array index
+     * @param token the input string token
+     * @return the array index. -1 if the token is "-"
+     * @throws JsonException if the string token is not in correct format
+     */
+    static private int getIndex(String token) {
+        if (token == null || token.length() == 0) {
+            throw new JsonException(JsonMessages.POINTER_ARRAY_INDEX_ERR(token));
+        }
+        if (token.equals("-")) {
+            return -1;
+        }
+        if (token.equals("0")) {
+            return 0;
+        }
+        if (token.charAt(0) == '+' || token.charAt(0) == '-') {
+            throw new JsonException(JsonMessages.POINTER_ARRAY_INDEX_ERR(token));
+        }
+        try {
+            return Integer.parseInt(token);
+        } catch (NumberFormatException ex) {
+            throw new JsonException(JsonMessages.POINTER_ARRAY_INDEX_ILLEGAL(token), ex);
+       }
+    }
+}
Index: trunk/src/org/glassfish/json/JsonPrettyGeneratorImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonPrettyGeneratorImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonPrettyGeneratorImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -117,4 +117,10 @@
     }
 
+    @Override
+    protected void writeColon() {
+        super.writeColon();
+        writeChar(' ');
+    }
+
     private void writeNewLine() {
         writeChar('\n');
Index: trunk/src/org/glassfish/json/JsonProviderImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonProviderImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonProviderImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -53,10 +53,15 @@
 import java.io.Reader;
 import java.io.Writer;
+import java.util.Collection;
 import java.util.Collections;
 import java.util.HashMap;
 import java.util.Map;
+import java.math.BigDecimal;
+import java.math.BigInteger;
 
 /**
  * @author Jitendra Kotamraju
+ * @author Kin-man Chung
+ * @author Alex Soto
  */
 public class JsonProviderImpl extends JsonProvider {
@@ -106,5 +111,5 @@
             pool = bufferPool;
         } else {
-            providerConfig = new HashMap<String, Object>();
+            providerConfig = new HashMap<>();
             if (prettyPrinting=JsonProviderImpl.isPrettyPrintingEnabled(config)) {
                 providerConfig.put(JsonGenerator.PRETTY_PRINTING, true);
@@ -152,5 +157,5 @@
             pool = bufferPool;
         } else {
-            providerConfig = new HashMap<String, Object>();
+            providerConfig = new HashMap<>();
             if (prettyPrinting=JsonProviderImpl.isPrettyPrintingEnabled(config)) {
                 providerConfig.put(JsonGenerator.PRETTY_PRINTING, true);
@@ -185,6 +190,91 @@
 
     @Override
+    public JsonObjectBuilder createObjectBuilder(JsonObject object) {
+        return new JsonObjectBuilderImpl(object, bufferPool);
+    }
+
+    @Override
+    public JsonObjectBuilder createObjectBuilder(Map<String, Object> map) {
+        return new JsonObjectBuilderImpl(map, bufferPool);
+    }
+
+    @Override
     public JsonArrayBuilder createArrayBuilder() {
         return new JsonArrayBuilderImpl(bufferPool);
+    }
+
+    @Override
+    public JsonArrayBuilder createArrayBuilder(JsonArray array) {
+        return new JsonArrayBuilderImpl(array, bufferPool);
+    }
+
+    @Override
+    public JsonArrayBuilder createArrayBuilder(Collection<?> collection) {
+        return new JsonArrayBuilderImpl(collection, bufferPool);
+    }
+
+    @Override
+    public JsonPointer createPointer(String jsonPointer) {
+        return new JsonPointerImpl(jsonPointer);
+    }
+
+    @Override
+    public JsonPatchBuilder createPatchBuilder() {
+        return new JsonPatchBuilderImpl();
+    }
+
+    @Override
+    public JsonPatchBuilder createPatchBuilder(JsonArray array) {
+        return new JsonPatchBuilderImpl(array);
+    }
+
+    @Override
+    public JsonPatch createPatch(JsonArray array) {
+        return new JsonPatchImpl(array);
+    }
+
+    @Override
+    public JsonPatch createDiff(JsonStructure source, JsonStructure target) {
+        return new JsonPatchImpl(JsonPatchImpl.diff(source, target));
+    }
+
+    @Override
+    public JsonMergePatch createMergePatch(JsonValue patch) {
+        return new JsonMergePatchImpl(patch);
+    }
+
+    @Override
+    public JsonMergePatch createMergeDiff(JsonValue source, JsonValue target) {
+        return new JsonMergePatchImpl(JsonMergePatchImpl.diff(source, target));
+    }
+
+    @Override
+    public JsonString createValue(String value) {
+        return new JsonStringImpl(value);
+    }
+
+    @Override
+    public JsonNumber createValue(int value) {
+        return JsonNumberImpl.getJsonNumber(value);
+    }
+
+    @Override
+    public JsonNumber createValue(long value) {
+        return JsonNumberImpl.getJsonNumber(value);
+    }
+
+    @Override
+    public JsonNumber createValue(double value) {
+        return JsonNumberImpl.getJsonNumber(value);
+    }
+
+    @Override
+    public JsonNumber createValue(BigInteger value) {
+        return JsonNumberImpl.getJsonNumber(value);
+    }
+
+    @Override
+    public JsonNumber createValue(BigDecimal value) {
+        return JsonNumberImpl.getJsonNumber(value);
     }
 
Index: trunk/src/org/glassfish/json/JsonReaderFactoryImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonReaderFactoryImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonReaderFactoryImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
Index: trunk/src/org/glassfish/json/JsonReaderImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonReaderImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonReaderImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -43,10 +43,15 @@
 import org.glassfish.json.api.BufferPool;
 
-import javax.json.*;
-import javax.json.stream.JsonParser;
 import java.io.InputStream;
 import java.io.Reader;
-import java.math.BigDecimal;
 import java.nio.charset.Charset;
+import javax.json.JsonArray;
+import javax.json.JsonException;
+import javax.json.JsonObject;
+import javax.json.JsonReader;
+import javax.json.JsonStructure;
+import javax.json.JsonValue;
+import javax.json.stream.JsonParser;
+import javax.json.stream.JsonParsingException;
 
 /**
@@ -82,12 +87,16 @@
         readDone = true;
         if (parser.hasNext()) {
-            JsonParser.Event e = parser.next();
-            if (e == JsonParser.Event.START_ARRAY) {
-                return readArray(new JsonArrayBuilderImpl(bufferPool));
-            } else if (e == JsonParser.Event.START_OBJECT) {
-                return readObject(new JsonObjectBuilderImpl(bufferPool));
+            try {
+                JsonParser.Event e = parser.next();
+                if (e == JsonParser.Event.START_ARRAY) {
+                    return parser.getArray();
+                } else if (e == JsonParser.Event.START_OBJECT) {
+                    return parser.getObject();
+                }
+            } catch (IllegalStateException ise) {
+                throw new JsonParsingException(ise.getMessage(), ise, parser.getLastCharLocation());
             }
         }
-        throw new JsonException("Internal Error");
+        throw new JsonException(JsonMessages.INTERNAL_ERROR());
     }
 
@@ -99,12 +108,12 @@
         readDone = true;
         if (parser.hasNext()) {
-            JsonParser.Event e = parser.next();
-            if (e == JsonParser.Event.START_OBJECT) {
-                return readObject(new JsonObjectBuilderImpl(bufferPool));
-            } else if (e == JsonParser.Event.START_ARRAY) {
-                throw new JsonException(JsonMessages.READER_EXPECTED_OBJECT_GOT_ARRAY());
+            try {
+                parser.next();
+                return parser.getObject();
+            } catch (IllegalStateException ise) {
+                throw new JsonParsingException(ise.getMessage(), ise, parser.getLastCharLocation());
             }
         }
-        throw new JsonException("Internal Error");
+        throw new JsonException(JsonMessages.INTERNAL_ERROR());
     }
 
@@ -116,12 +125,29 @@
         readDone = true;
         if (parser.hasNext()) {
-            JsonParser.Event e = parser.next();
-            if (e == JsonParser.Event.START_ARRAY) {
-                return readArray(new JsonArrayBuilderImpl(bufferPool));
-            } else if (e == JsonParser.Event.START_OBJECT) {
-                throw new JsonException(JsonMessages.READER_EXPECTED_ARRAY_GOT_OBJECT());
+            try {
+                parser.next();
+                return parser.getArray();
+            } catch (IllegalStateException ise) {
+                throw new JsonParsingException(ise.getMessage(), ise, parser.getLastCharLocation());
             }
         }
-        throw new JsonException("Internal Error");
+        throw new JsonException(JsonMessages.INTERNAL_ERROR());
+    }
+
+    @Override
+    public JsonValue readValue() {
+        if (readDone) {
+            throw new IllegalStateException(JsonMessages.READER_READ_ALREADY_CALLED());
+        }
+        readDone = true;
+        if (parser.hasNext()) {
+            try {
+                parser.next();
+                return parser.getValue();
+            } catch (IllegalStateException ise) {
+                throw new JsonParsingException(ise.getMessage(), ise, parser.getLastCharLocation());
+            }
+        }
+        throw new JsonException(JsonMessages.INTERNAL_ERROR());
     }
 
@@ -131,88 +157,3 @@
         parser.close();
     }
-
-    private JsonArray readArray(JsonArrayBuilder builder) {
-        while(parser.hasNext()) {
-            JsonParser.Event e = parser.next();
-            switch (e) {
-                case START_ARRAY:
-                    JsonArray array = readArray(new JsonArrayBuilderImpl(bufferPool));
-                    builder.add(array);
-                    break;
-                case START_OBJECT:
-                    JsonObject object = readObject(new JsonObjectBuilderImpl(bufferPool));
-                    builder.add(object);
-                    break;
-                case VALUE_STRING:
-                    builder.add(parser.getString());
-                    break;
-                case VALUE_NUMBER:
-                    if (parser.isDefinitelyInt()) {
-                        builder.add(parser.getInt());
-                    } else {
-                        builder.add(parser.getBigDecimal());
-                    }
-                    break;
-                case VALUE_TRUE:
-                    builder.add(JsonValue.TRUE);
-                    break;
-                case VALUE_FALSE:
-                    builder.add(JsonValue.FALSE);
-                    break;
-                case VALUE_NULL:
-                    builder.addNull();
-                    break;
-                case END_ARRAY:
-                    return builder.build();
-                default:
-                    throw new JsonException("Internal Error");
-            }
-        }
-        throw new JsonException("Internal Error");
-    }
-
-    private JsonObject readObject(JsonObjectBuilder builder) {
-        String key = null;
-        while(parser.hasNext()) {
-            JsonParser.Event e = parser .next();
-            switch (e) {
-                case START_ARRAY:
-                    JsonArray array = readArray(new JsonArrayBuilderImpl(bufferPool));
-                    builder.add(key, array);
-                    break;
-                case START_OBJECT:
-                    JsonObject object = readObject(new JsonObjectBuilderImpl(bufferPool));
-                    builder.add(key, object);
-                    break;
-                case KEY_NAME:
-                    key = parser.getString();
-                    break;
-                case VALUE_STRING:
-                    builder.add(key, parser.getString());
-                    break;
-                case VALUE_NUMBER:
-                    if (parser.isDefinitelyInt()) {
-                        builder.add(key, parser.getInt());
-                    } else {
-                        builder.add(key, parser.getBigDecimal());
-                    }
-                    break;
-                case VALUE_TRUE:
-                    builder.add(key, JsonValue.TRUE);
-                    break;
-                case VALUE_FALSE:
-                    builder.add(key, JsonValue.FALSE);
-                    break;
-                case VALUE_NULL:
-                    builder.addNull(key);
-                    break;
-                case END_OBJECT:
-                    return builder.build();
-                default:
-                    throw new JsonException("Internal Error");
-            }
-        }
-        throw new JsonException("Internal Error");
-    }
-
 }
Index: trunk/src/org/glassfish/json/JsonStringImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonStringImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonStringImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -78,4 +78,7 @@
     @Override
     public boolean equals(Object obj) {
+        if (this == obj){
+            return true;
+        }
         if (!(obj instanceof JsonString)) {
             return false;
Index: trunk/src/org/glassfish/json/JsonStructureParser.java
===================================================================
--- trunk/src/org/glassfish/json/JsonStructureParser.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonStructureParser.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -45,5 +45,9 @@
 import javax.json.stream.JsonParser;
 import java.math.BigDecimal;
-import java.util.*;
+import java.util.ArrayDeque;
+import java.util.Deque;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.NoSuchElementException;
 
 /**
@@ -56,5 +60,5 @@
     private Scope current;
     private Event state;
-    private final Deque<Scope> scopeStack = new ArrayDeque<Scope>();
+    private final Deque<Scope> scopeStack = new ArrayDeque<>();
 
     JsonStructureParser(JsonArray array) {
@@ -68,10 +72,14 @@
     @Override
     public String getString() {
-        if (state == Event.KEY_NAME) {
-            return ((ObjectScope)current).key;
-        } else if (state == Event.VALUE_STRING) {
-            return ((JsonString)current.getJsonValue()).getString();
-        }
-        throw new IllegalStateException(JsonMessages.PARSER_GETSTRING_ERR(state));
+        switch (state) {
+            case KEY_NAME:
+                return ((ObjectScope)current).key;
+            case VALUE_STRING:
+                return ((JsonString)current.getJsonValue()).getString();
+            case VALUE_NUMBER:
+                return ((JsonNumber)current.getJsonValue()).toString();
+            default:
+                throw new IllegalStateException(JsonMessages.PARSER_GETSTRING_ERR(state));
+        }
     }
 
@@ -168,4 +176,60 @@
     public void close() {
         // no-op
+    }
+
+    @Override
+    public void skipObject() {
+        if (current instanceof ObjectScope) {
+            int depth = 1;
+            do {
+                if (state == Event.KEY_NAME) {
+                    state = getState(current.getJsonValue());
+                    switch (state) {
+                        case START_OBJECT:
+                            depth++;
+                            break;
+                        case END_OBJECT:
+                            depth--;
+                            break;
+                        default:
+                            //no-op
+                    }
+                } else {
+                    if (current.hasNext()) {
+                        current.next();
+                        state = Event.KEY_NAME;
+                    } else {
+                        state = Event.END_OBJECT;
+                        depth--;
+                    }
+                }
+            } while (state != Event.END_OBJECT && depth > 0);
+        }
+    }
+
+    @Override
+    public void skipArray() {
+        if (current instanceof ArrayScope) {
+            int depth = 1;
+            do {
+                if (current.hasNext()) {
+                    current.next();
+                    state = getState(current.getJsonValue());
+                    switch (state) {
+                        case START_ARRAY:
+                            depth++;
+                            break;
+                        case END_ARRAY:
+                            depth--;
+                            break;
+                        default:
+                            //no-op
+                    }
+                } else {
+                    state = Event.END_ARRAY;
+                    depth--;
+                }
+            } while (!(state == Event.END_ARRAY && depth == 0));
+        }
     }
 
@@ -187,5 +251,5 @@
                 return Event.VALUE_NULL;
             default:
-                throw new JsonException("Unknown value type="+value.getValueType());
+                throw new JsonException(JsonMessages.PARSER_STATE_ERR(value.getValueType()));
         }
     }
@@ -200,5 +264,5 @@
                 return new ObjectScope((JsonObject)value);
             }
-            throw new JsonException("Cannot be called for value="+value);
+            throw new JsonException(JsonMessages.PARSER_SCOPE_ERR(value));
         }
     }
Index: trunk/src/org/glassfish/json/JsonTokenizer.java
===================================================================
--- trunk/src/org/glassfish/json/JsonTokenizer.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonTokenizer.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -293,6 +293,9 @@
             }
         }
-        readBegin--;
-        storeEnd = readBegin;
+        if (ch != -1) {
+            // Only reset readBegin if eof has not been reached
+            readBegin--;
+            storeEnd = readBegin;
+        }
     }
 
@@ -417,4 +420,47 @@
     }
 
+    boolean hasNextToken() {
+        reset();
+        int ch = peek();
+
+        // whitespace
+        while (ch == 0x20 || ch == 0x09 || ch == 0x0a || ch == 0x0d) {
+            if (ch == '\r') {
+                ++lineNo;
+                ++readBegin;
+                ch = peek();
+                if (ch == '\n') {
+                    lastLineOffset = bufferOffset+readBegin+1;
+                } else {
+                    lastLineOffset = bufferOffset+readBegin;
+                    continue;
+                }
+            } else if (ch == '\n') {
+                ++lineNo;
+                lastLineOffset = bufferOffset+readBegin+1;
+            }
+            ++readBegin;
+            ch = peek();
+        }
+        return ch != -1;
+    }
+
+    private int peek() {
+        try {
+            if (readBegin == readEnd) {     // need to fill the buffer
+                int len = fillBuf();
+                if (len == -1) {
+                    return -1;
+                }
+                assert len != 0;
+                readBegin = storeEnd;
+                readEnd = readBegin+len;
+            }
+            return buf[readBegin];
+        } catch (IOException ioe) {
+            throw new JsonException(JsonMessages.TOKENIZER_IO_ERR(), ioe);
+        }
+    }
+
     // Gives the location of the last char. Used for
     // JsonParsingException.getLocation
@@ -499,5 +545,5 @@
         // no need to create BigDecimal for common integer values (1-9 digits)
         int storeLen = storeEnd-storeBegin;
-        if (!fracOrExp && (storeLen <= 9 || (minus && storeLen == 10))) {
+        if (!fracOrExp && (storeLen <= 9 || (minus && storeLen <= 10))) {
             int num = 0;
             int i = minus ? 1 : 0;
@@ -510,4 +556,19 @@
         }
     }
+    
+    long getLong() {
+        // no need to create BigDecimal for common integer values (1-18 digits)
+        int storeLen = storeEnd-storeBegin;
+        if (!fracOrExp && (storeLen <= 18 || (minus && storeLen <= 19))) {
+            long num = 0;
+            int i = minus ? 1 : 0;
+            for(; i < storeLen; i++) {
+                num = num * 10 + (buf[storeBegin+i] - '0');
+            }
+            return minus ? -num : num;
+        } else {
+            return getBigDecimal().longValue();
+        }
+    }
 
     // returns true for common integer values (1-9 digits).
@@ -515,5 +576,12 @@
     boolean isDefinitelyInt() {
         int storeLen = storeEnd-storeBegin;
-        return !fracOrExp && (storeLen <= 9 || (minus && storeLen == 10));
+        return !fracOrExp && (storeLen <= 9 || (minus && storeLen <= 10));
+    }
+    
+    // returns true for common long values (1-18 digits).
+    // So there are cases it will return false even though the number is long
+    boolean isDefinitelyLong() {
+    	int storeLen = storeEnd-storeBegin;
+    	return !fracOrExp && (storeLen <= 18 || (minus && storeLen <= 19));
     }
 
Index: trunk/src/org/glassfish/json/JsonUtil.java
===================================================================
--- trunk/src/org/glassfish/json/JsonUtil.java	(revision 13231)
+++ trunk/src/org/glassfish/json/JsonUtil.java	(revision 13231)
@@ -0,0 +1,99 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import java.io.StringReader;
+import javax.json.Json;
+import javax.json.JsonReader;
+import javax.json.JsonValue;
+import javax.json.stream.JsonParsingException;
+
+/**
+ * A utility class
+ * 
+ * @since 1.1
+ */
+public final class JsonUtil {
+
+    private JsonUtil() {
+    }
+
+    /**
+     * Reads the input JSON text and returns a JsonValue.
+     * <p>For convenience, single quotes as well as double quotes
+     * are allowed to delimit JSON strings. If single quotes are
+     * used, any quotes, single or double, in the JSON string must be
+     * escaped (prepend with a '\').
+     *
+     * @param jsonString the input JSON data
+     * @return the object model for {@code jsonString}
+     * @throws JsonParsingException if the input is not legal JSON text
+     */
+    public static JsonValue toJson(String jsonString) {
+        StringBuilder builder = new StringBuilder();
+        boolean single_context = false;
+        for (int i = 0; i < jsonString.length(); i++) {
+            char ch = jsonString.charAt(i);
+            if (ch == '\\') {
+                i = i + 1;
+                if (i < jsonString.length()) {
+                    ch = jsonString.charAt(i);
+                    if (!(single_context && ch == '\'')) {
+                        // unescape ' inside single quotes
+                        builder.append('\\');
+                    }
+                }
+            } else if (ch == '\'') {
+                // Turn ' into ", for proper JSON string
+                ch = '"';
+                single_context = ! single_context;
+            }
+            builder.append(ch);
+        }
+                   
+        JsonReader reader = Json.createReader(
+                                new StringReader(builder.toString()));
+        JsonValue value = reader.readValue();
+        reader.close();
+        return value;
+    }
+}
+
Index: trunk/src/org/glassfish/json/JsonWriterFactoryImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonWriterFactoryImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonWriterFactoryImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
Index: trunk/src/org/glassfish/json/JsonWriterImpl.java
===================================================================
--- trunk/src/org/glassfish/json/JsonWriterImpl.java	(revision 13230)
+++ trunk/src/org/glassfish/json/JsonWriterImpl.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -49,4 +49,5 @@
 import java.io.Writer;
 import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
 import java.util.Map;
 
@@ -57,5 +58,4 @@
  */
 class JsonWriterImpl implements JsonWriter {
-    private static final Charset UTF_8 = Charset.forName("UTF-8");
 
     private final JsonGeneratorImpl generator;
@@ -75,9 +75,9 @@
 
     JsonWriterImpl(OutputStream out, BufferPool bufferPool) {
-        this(out, UTF_8, false, bufferPool);
+        this(out, StandardCharsets.UTF_8, false, bufferPool);
     }
 
     JsonWriterImpl(OutputStream out, boolean prettyPrinting, BufferPool bufferPool) {
-        this(out, UTF_8, prettyPrinting, bufferPool);
+        this(out, StandardCharsets.UTF_8, prettyPrinting, bufferPool);
     }
 
@@ -146,4 +146,26 @@
 
     @Override
+    public void write(JsonValue value) {
+        switch (value.getValueType()) {
+            case OBJECT:
+                writeObject((JsonObject) value);
+                return;
+            case ARRAY:
+                writeArray((JsonArray) value);
+                return;
+            default:
+                if (writeDone) {
+                    throw new IllegalStateException(JsonMessages.WRITER_WRITE_ALREADY_CALLED());
+                }
+                writeDone = true;
+                generator.write(value);
+                generator.flushBuffer();
+                if (os != null) {
+                    generator.flush();
+                }
+        }
+    }
+
+    @Override
     public void close() {
         writeDone = true;
Index: trunk/src/org/glassfish/json/MapUtil.java
===================================================================
--- trunk/src/org/glassfish/json/MapUtil.java	(revision 13231)
+++ trunk/src/org/glassfish/json/MapUtil.java	(revision 13231)
@@ -0,0 +1,115 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import org.glassfish.json.api.BufferPool;
+
+import javax.json.JsonArrayBuilder;
+import javax.json.JsonObjectBuilder;
+import javax.json.JsonValue;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.util.Collection;
+import java.util.Map;
+
+/**
+ * Util for transforming a Map to a Json objects.
+ *
+ * @author asotobu
+ */
+public final class MapUtil {
+
+    private MapUtil() {
+        super();
+    }
+
+    static JsonValue handle(Object value, BufferPool bufferPool) {
+
+        if (value == null) {
+            return JsonValue.NULL;
+        }
+
+        if (value instanceof BigDecimal) {
+            return JsonNumberImpl.getJsonNumber((BigDecimal) value);
+        } else {
+            if (value instanceof BigInteger) {
+                return JsonNumberImpl.getJsonNumber((BigInteger) value);
+            } else {
+                if ( value instanceof Boolean) {
+                    Boolean b = (Boolean) value;
+                    return b ? JsonValue.TRUE : JsonValue.FALSE;
+                } else {
+                    if (value instanceof Double) {
+                        return JsonNumberImpl.getJsonNumber((Double) value);
+                    } else {
+                        if (value instanceof Integer) {
+                            return JsonNumberImpl.getJsonNumber((Integer) value);
+                        } else {
+                            if (value instanceof Long) {
+                                return JsonNumberImpl.getJsonNumber((Long) value);
+                            } else {
+                                if (value instanceof String) {
+                                    return new JsonStringImpl((String) value);
+                                } else {
+                                    if (value instanceof Collection) {
+                                        @SuppressWarnings("unchecked")
+                                        Collection<?> collection = (Collection<?>) value;
+                                        JsonArrayBuilder jsonArrayBuilder = new JsonArrayBuilderImpl(collection, bufferPool);
+                                        return jsonArrayBuilder.build();
+                                    } else {
+                                        if (value instanceof Map) {
+                                            @SuppressWarnings("unchecked")
+                                            JsonObjectBuilder object = new JsonObjectBuilderImpl((Map<String, Object>) value, bufferPool);
+                                            return object.build();
+                                        }
+                                    }
+                                }
+                            }
+                        }
+                    }
+                }
+            }
+        }
+
+        throw new IllegalArgumentException(String.format("Type %s is not supported.", value.getClass()));
+    }
+
+}
Index: trunk/src/org/glassfish/json/NodeReference.java
===================================================================
--- trunk/src/org/glassfish/json/NodeReference.java	(revision 13231)
+++ trunk/src/org/glassfish/json/NodeReference.java	(revision 13231)
@@ -0,0 +1,307 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2015-2017 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License").  You
+ * may not use this file except in compliance with the License.  You can
+ * obtain a copy of the License at
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license."  If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above.  However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+
+package org.glassfish.json;
+
+import javax.json.Json;
+import javax.json.JsonArray;
+import javax.json.JsonArrayBuilder;
+import javax.json.JsonException;
+import javax.json.JsonObject;
+import javax.json.JsonStructure;
+import javax.json.JsonValue;
+
+/**
+ * This class is a helper class for JsonPointer implementation,
+ * and is not part of the API.
+ *
+ * This class encapsulates a reference to a JSON node.
+ * There are three types of references.
+ * <ol><li>a reference to the root of a JSON tree.</li>
+ *     <li>a reference to a name/value (possibly non-existing) pair of a JSON object, identified by a name.</li>
+ *     <li>a reference to a member value of a JSON array, identified by an index.</li>
+ * </ol>
+ * Static factory methods are provided for creating these references.
+ *
+ * <p>A referenced value can be retrieved or replaced.
+ * The value of a JSON object or JSON array can be
+ * removed.  A new value can be added to a JSON object or
+ * inserted into a JSON array</p>
+ *
+ * <p>Since a {@code JsonObject} or {@code JsonArray} is immutable, these operations
+ * must not modify the referenced JSON object or array. The methods {@link #add},
+ * {@link #replace}, and {@link #remove} returns a new
+ * JSON object or array after the execution of the operation.</p>
+ */
+abstract class NodeReference {
+
+    /**
+     * Return {@code true} if a reference points to a valid value, {@code false} otherwise.
+     *
+     * @return {@code true} if a reference points to a value
+     */
+    abstract public boolean contains();
+
+    /**
+     * Get the value at the referenced location.
+     *
+     * @return the JSON value referenced
+     * @throws JsonException if the referenced value does not exist
+     */
+    abstract public JsonValue get();
+
+    /**
+     * Add or replace a value at the referenced location.
+     * If the reference is the root of a JSON tree, the added value must be
+     * a JSON object or array, which becomes the referenced JSON value.
+     * If the reference is an index of a JSON array, the value is inserted
+     * into the array at the index.  If the index is -1, the value is
+     * appended to the array.
+     * If the reference is a name of a JSON object, the name/value pair is added
+     * to the object, replacing any pair with the same name.
+     *
+     * @param value the value to be added
+     * @return the JsonStructure after the operation
+     * @throws JsonException if the index to the array is not -1 or is out of range
+     */
+    abstract public JsonStructure add(JsonValue value);
+
+    /**
+     * Remove the name/value pair from the JSON object, or the value in a JSON array, as specified by the reference
+     *
+     * @return the JsonStructure after the operation
+     * @throws JsonException if the name/value pair of the referenced JSON object
+     *    does not exist, or if the index of the referenced JSON array is
+     *    out of range, or if the reference is a root reference
+     */
+    abstract public JsonStructure remove();
+
+    /**
+     * Replace the referenced value with the specified value.
+     *
+     * @param value the JSON value to be stored at the referenced location
+     * @return the JsonStructure after the operation
+     * @throws JsonException if the name/value pair of the referenced JSON object
+     *    does not exist, or if the index of the referenced JSON array is
+     *    out of range, or if the reference is a root reference
+     */
+    abstract public JsonStructure replace(JsonValue value);
+
+    /**
+     * Returns a {@code NodeReference} for a {@code JsonStructure}.
+     *
+     * @param structure the {@code JsonStructure} referenced
+     * @return the {@code NodeReference}
+     */
+    public static NodeReference of(JsonStructure structure) {
+        return new RootReference(structure);
+    }
+
+    /**
+     * Returns a {@code NodeReference} for a name/value pair in a
+     * JSON object.
+     *
+     * @param object the referenced JSON object
+     * @param name the name of the name/pair
+     * @return the {@code NodeReference}
+     */
+    public static NodeReference of(JsonObject object, String name) {
+        return new ObjectReference(object, name);
+    }
+
+    /**
+     * Returns a {@code NodeReference} for a member value in a
+     * JSON array.
+     *
+     * @param array the referenced JSON array
+     * @param index the index of the member value in the JSON array
+     * @return the {@code NodeReference}
+     */
+    public static NodeReference of(JsonArray array, int index) {
+        return new ArrayReference(array, index);
+    }
+
+    static class RootReference extends NodeReference {
+
+        private JsonStructure root;
+
+        RootReference(JsonStructure root) {
+            this.root = root;
+        }
+
+        @Override
+        public boolean contains() {
+            return root != null;
+        }
+
+        @Override
+        public JsonValue get() {
+            return root;
+        }
+
+        @Override
+        public JsonStructure add(JsonValue value) {
+            switch (value.getValueType() ) {
+                case OBJECT:
+                case ARRAY:
+                    this.root = (JsonStructure) value;
+                    break;
+                default:
+                    throw new JsonException(JsonMessages.NODEREF_VALUE_ADD_ERR());
+            }
+            return root;
+        }
+
+        @Override
+        public JsonStructure remove() {
+            throw new JsonException(JsonMessages.NODEREF_VALUE_CANNOT_REMOVE());
+        }
+
+        @Override
+        public JsonStructure replace(JsonValue value) {
+            return add(value);
+        }
+    }
+
+    static class ObjectReference extends NodeReference {
+
+        private final JsonObject object;
+        private final String key;
+
+        ObjectReference(JsonObject object, String key) {
+            this.object = object;
+            this.key = key;
+        }
+
+        @Override
+        public boolean contains() {
+            return object != null && object.containsKey(key);
+        }
+
+        @Override
+        public JsonValue get() {
+            if (!contains()) {
+                throw new JsonException(JsonMessages.NODEREF_OBJECT_MISSING(key));
+            }
+            return object.get(key);
+        }
+
+        @Override
+        public JsonObject add(JsonValue value) {
+            return Json.createObjectBuilder(object).add(key, value).build();
+        }
+
+        @Override
+        public JsonObject remove() {
+            if (!contains()) {
+                throw new JsonException(JsonMessages.NODEREF_OBJECT_MISSING(key));
+            }
+            return Json.createObjectBuilder(object).remove(key).build();
+        }
+
+        @Override
+        public JsonObject replace(JsonValue value) {
+            if (!contains()) {
+                throw new JsonException(JsonMessages.NODEREF_OBJECT_MISSING(key));
+            }
+            return add(value);
+        }
+    }
+
+    static class ArrayReference extends NodeReference {
+
+        private final JsonArray array;
+        private final int index; // -1 means "-" in JSON Pointer
+
+        ArrayReference(JsonArray array, int index) {
+            this.array = array;
+            this.index = index;
+        }
+
+        @Override
+        public boolean contains() {
+            return array != null && index > -1 && index < array.size();
+        }
+
+        @Override
+        public JsonValue get() {
+            if (!contains()) {
+                throw new JsonException(JsonMessages.NODEREF_ARRAY_INDEX_ERR(index, array.size()));
+            }
+            return array.get(index);
+        }
+
+        @Override
+        public JsonArray add(JsonValue value) {
+            //TODO should we check for arrayoutofbounds?
+            // The spec seems to say index = array.size() is allowed. This is handled as append
+            JsonArrayBuilder builder = Json.createArrayBuilder(this.array);
+            if (index == -1 || index == array.size()) {
+                builder.add(value);
+            } else {
+                if(index < array.size()) {
+                    builder.add(index, value);
+                } else {
+                    throw new JsonException(JsonMessages.NODEREF_ARRAY_INDEX_ERR(index, array.size()));
+                }
+            }
+            return builder.build();
+        }
+
+        @Override
+        public JsonArray remove() {
+            if (!contains()) {
+                throw new JsonException(JsonMessages.NODEREF_ARRAY_INDEX_ERR(index, array.size()));
+            }
+            JsonArrayBuilder builder = Json.createArrayBuilder(this.array);
+            return builder.remove(index).build();
+        }
+
+        @Override
+        public JsonArray replace(JsonValue value) {
+            if (!contains()) {
+                throw new JsonException(JsonMessages.NODEREF_ARRAY_INDEX_ERR(index, array.size()));
+            }
+            JsonArrayBuilder builder = Json.createArrayBuilder(this.array);
+            return builder.set(index, value).build();
+        }
+    }
+}
+
Index: trunk/src/org/glassfish/json/UnicodeDetectingInputStream.java
===================================================================
--- trunk/src/org/glassfish/json/UnicodeDetectingInputStream.java	(revision 13230)
+++ trunk/src/org/glassfish/json/UnicodeDetectingInputStream.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2012-2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -46,4 +46,5 @@
 import java.io.InputStream;
 import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
 
 /**
@@ -54,7 +55,5 @@
  */
 class UnicodeDetectingInputStream extends FilterInputStream {
-    private static final Charset UTF_8 = Charset.forName("UTF-8");
-    private static final Charset UTF_16BE = Charset.forName("UTF-16BE");
-    private static final Charset UTF_16LE = Charset.forName("UTF-16LE");
+
     private static final Charset UTF_32LE = Charset.forName("UTF-32LE");
     private static final Charset UTF_32BE = Charset.forName("UTF-32BE");
@@ -122,5 +121,5 @@
             buf[3] = (byte)b4;
         } catch (IOException ioe) {
-            throw new JsonException("I/O error while auto-detecting the encoding of stream", ioe);
+            throw new JsonException(JsonMessages.PARSER_INPUT_ENC_DETECT_IOERR(), ioe);
         }
     }
@@ -129,5 +128,5 @@
         fillBuf();
         if (bufLen < 2) {
-            throw new JsonException("Cannot auto-detect encoding, not enough chars");
+            throw new JsonException(JsonMessages.PARSER_INPUT_ENC_DETECT_FAILED());
         } else if (bufLen == 4) {
             // Use BOM to detect encoding
@@ -140,11 +139,11 @@
             } else if (buf[0] == FE && buf[1] == FF) {
                 curIndex = 2;
-                return UTF_16BE;
+                return StandardCharsets.UTF_16BE;
             } else if (buf[0] == FF && buf[1] == FE) {
                 curIndex = 2;
-                return UTF_16LE;
+                return StandardCharsets.UTF_16LE;
             } else if (buf[0] == EF && buf[1] == BB && buf[2] == BF) {
                 curIndex = 3;
-                return UTF_8;
+                return StandardCharsets.UTF_8;
             }
             // No BOM, just use JSON RFC's encoding algo to auto-detect
@@ -152,12 +151,12 @@
                 return UTF_32BE;
             } else if (buf[0] == NUL && buf[2] == NUL) {
-                return UTF_16BE;
+                return StandardCharsets.UTF_16BE;
             } else if (buf[1] == NUL && buf[2] == NUL && buf[3] == NUL) {
                 return UTF_32LE;
             } else if (buf[1] == NUL && buf[3] == NUL) {
-                return UTF_16LE;
+                return StandardCharsets.UTF_16LE;
             }
         }
-        return UTF_8;
+        return StandardCharsets.UTF_8;
     }
 
Index: trunk/src/org/glassfish/json/api/BufferPool.java
===================================================================
--- trunk/src/org/glassfish/json/api/BufferPool.java	(revision 13230)
+++ trunk/src/org/glassfish/json/api/BufferPool.java	(revision 13231)
@@ -2,5 +2,5 @@
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
  *
- * Copyright (c) 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
  *
  * The contents of this file are subject to the terms of either the GNU
@@ -9,10 +9,10 @@
  * may not use this file except in compliance with the License.  You can
  * obtain a copy of the License at
- * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
- * or packager/legal/LICENSE.txt.  See the License for the specific
+ * https://oss.oracle.com/licenses/CDDL+GPL-1.1
+ * or LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
- * file and include the License file at packager/legal/LICENSE.txt.
+ * file and include the License file at LICENSE.txt.
  *
  * GPL Classpath Exception:
@@ -61,4 +61,6 @@
     /**
      * Returns an object back to the pool.
+     *
+     * @param buf object to return back to the pool
      */
     void recycle(char[] buf);
Index: trunk/src/org/glassfish/json/messages.properties
===================================================================
--- trunk/src/org/glassfish/json/messages.properties	(revision 13231)
+++ trunk/src/org/glassfish/json/messages.properties	(revision 13231)
@@ -0,0 +1,112 @@
+#
+# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+#
+# Copyright (c) 2013-2017 Oracle and/or its affiliates. All rights reserved.
+#
+# The contents of this file are subject to the terms of either the GNU
+# General Public License Version 2 only ("GPL") or the Common Development
+# and Distribution License("CDDL") (collectively, the "License").  You
+# may not use this file except in compliance with the License.  You can
+# obtain a copy of the License at
+# https://oss.oracle.com/licenses/CDDL+GPL-1.1
+# or LICENSE.txt.  See the License for the specific
+# language governing permissions and limitations under the License.
+#
+# When distributing the software, include this License Header Notice in each
+# file and include the License file at LICENSE.txt.
+#
+# GPL Classpath Exception:
+# Oracle designates this particular file as subject to the "Classpath"
+# exception as provided by Oracle in the GPL Version 2 section of the License
+# file that accompanied this code.
+#
+# Modifications:
+# If applicable, add the following below the License Header, with the fields
+# enclosed by brackets [] replaced by your own identifying information:
+# "Portions Copyright [year] [name of copyright owner]"
+#
+# Contributor(s):
+# If you wish your version of this file to be governed by only the CDDL or
+# only the GPL Version 2, indicate your decision by adding "[Contributor]
+# elects to include this software in this distribution under the [CDDL or GPL
+# Version 2] license."  If you don't indicate a single choice of license, a
+# recipient has the option to distribute your version of this file under
+# either the CDDL, the GPL Version 2 or to extend the choice of license to
+# its licensees as provided above.  However, if you add GPL Version 2 code
+# and therefore, elected the GPL Version 2 license, then the option applies
+# only if the new code is made subject to such option by the copyright
+# holder.
+#
+
+internal.error=Internal Error
+
+parser.getString.err=JsonParser#getString() is valid only for KEY_NAME, VALUE_STRING, VALUE_NUMBER parser states. \
+  But current parser state is {0}
+parser.isIntegralNumber.err=JsonParser#isIntegralNumber() is valid only for VALUE_NUMBER parser state. \
+  But current parser state is {0}
+parser.getInt.err=JsonParser#getInt() is valid only for VALUE_NUMBER parser state. \
+  But current parser state is {0}
+parser.getLong.err=JsonParser#getLong() is valid only for VALUE_NUMBER parser state. \
+  But current parser state is {0}
+parser.getBigDecimal.err=JsonParser#getBigDecimal() is valid only for VALUE_NUMBER parser state. \
+  But current parser state is {0}
+parser.getArray.err=JsonParser#getArray() or JsonParser#getArrayStream() is valid only for START_ARRAY parser state. \
+  But current parser state is {0}
+parser.getObject.err=JsonParser#getObject() or JsonParser#getObjectStream() is valid only for START_OBJECT parser state. \
+  But current parser state is {0}
+parser.getValue.err=JsonParser#getValue() is valid only for START_ARRAY, START_OBJECT, KEY_NAME, VALUE_STRING, VALUE_NUMBER, VALUE_NULL, VALUE_FALSE, VALUE_TRUE parser states. \
+  But current parser state is {0}
+parser.getValueStream.err=JsonParser#getValueStream() the parser must not be in an array or object. \
+  But current parser state is {0}
+parser.expected.eof=Expected EOF token, but got {0}
+parser.tokenizer.close.io=I/O error while closing JSON tokenizer
+parser.invalid.token=Invalid token={0} at {1}. Expected tokens are: {2}
+parser.state.err=Unknown value type {0}
+parser.scope.err=Cannot be called for value {0}
+parser.input.enc.detect.failed=Cannot auto-detect encoding, not enough chars
+parser.input.enc.detect.ioerr=I/O error while auto-detecting the encoding of stream
+
+generator.flush.io.err=I/O error while flushing generated JSON
+generator.close.io.err=I/O error while closing JsonGenerator
+generator.write.io.err=I/O error while writing in JsonGenerator
+generator.illegal.method=Illegal method during JSON generation, \
+  not valid in current context {0}
+generator.double.infinite.nan=double value cannot be Infinite or NaN
+generator.incomplete.json=Generating incomplete JSON
+generator.illegal.multiple.text=Cannot generate more than one JSON text
+
+writer.write.already.called=write/writeObject/writeArray/close method is already called
+
+reader.read.already.called=read/readObject/readArray/close method is already called
+
+objbuilder.name.null=Name in JsonObject's name/value pair cannot be null
+objbuilder.value.null=Value in JsonObject's name/value pair cannot be null
+objbuilder.object.builder.null=Object builder that is used to create a value in JsonObject's name/value pair cannot be null
+objbuilder.array.builder.null=Array builder that is used to create a value in JsonObject's name/value pair cannot be null
+
+arrbuilder.value.null=Cannot invoke add(null) while building JsonArray.
+arrbuilder.object.builder.null=Object builder that is used to add a value to JSON array cannot be null
+arrbuilder.array.builder.null=Array builder that is used to add a value to JSON array cannot be null
+arrbuilder.valuelist.null=Index: {0}, Size: {1}
+
+tokenizer.unexpected.char=Unexpected char {0} at {1}
+tokenizer.expected.char=Unexpected char {0} at {1}, expecting ''{2}''
+tokenizer.io.err=I/O error while parsing JSON
+
+pointer.format.invalid=A non-empty JSON Pointer must begin with a ''/''
+pointer.mapping.missing=The JSON Object ''{0}'' contains no mapping for the name ''{1}''
+pointer.reference.invalid=The reference value in a JSON Pointer must be a JSON Object or a JSON Array, was ''{0}''
+pointer.array.index.err=Array index format error, was ''{0}''
+pointer.array.index.illegal=Illegal integer format, was ''{0}''
+
+noderef.value.add.err=The root value only allows adding a JSON object or array
+noderef.value.cannot.remove=The JSON value at the root cannot be removed
+noderef.object.missing=Non-existing name/value pair in the object for key {0}
+noderef.array.index.err=An array item index is out of range. Index: {0}, Size: {1}
+
+patch.must.be.array=A JSON Patch must be an array of JSON Objects
+patch.move.proper.prefix=The ''{0}'' path of the patch operation ''move'' is a proper prefix of the ''{1}'' path
+patch.move.target.null=The ''{0}'' path of the patch operation ''move'' does not exist in target object
+patch.test.failed=The JSON Patch operation ''test'' failed for path ''{0}'' and value ''{1}''
+patch.illegal.operation=Illegal value for the op member of the JSON Patch operation: ''{0}''
+patch.member.missing=The JSON Patch operation ''{0}'' must contain a ''{1}'' member
