You are viewing a plain text version of this content. The canonical link for it is here.
Posted to derby-commits@db.apache.org by rh...@apache.org on 2015/07/13 22:29:49 UTC

svn commit: r1690814 - in /db/derby/code/trunk: ./ java/build/org/apache/derbyBuild/lastgoodjarcontents/ java/engine/org/apache/derby/catalog/ java/engine/org/apache/derby/impl/sql/compile/ java/optional/ java/optional/org/apache/derby/optional/api/ ja...

Author: rhillegas
Date: Mon Jul 13 20:29:48 2015
New Revision: 1690814

URL: http://svn.apache.org/r1690814
Log:
DERBY-6825: First rev of the simpleJson optional tool.

Added:
    db/derby/code/trunk/java/optional/org/apache/derby/optional/api/SimpleJsonUtils.java   (with props)
    db/derby/code/trunk/java/optional/org/apache/derby/optional/json/
    db/derby/code/trunk/java/optional/org/apache/derby/optional/json/SimpleJsonTool.java   (with props)
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/JsonSuite.java   (with props)
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SimpleJsonTest.java   (with props)
    db/derby/code/trunk/tools/java/json_simple-1.1.jar   (with props)
    db/derby/code/trunk/tools/release/notices/simpleJson.txt   (with props)
Modified:
    db/derby/code/trunk/build.xml
    db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyTesting.jar.lastcontents
    db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyoptionaltools.jar.lastcontents
    db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyTesting.jar.lastcontents
    db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyoptionaltools.jar.lastcontents
    db/derby/code/trunk/java/engine/org/apache/derby/catalog/Java5SystemProcedures.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/StaticMethodCallNode.java
    db/derby/code/trunk/java/optional/build.xml
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/_Suite.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/build.xml
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/JDBC.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/TestConfiguration.java
    db/derby/code/trunk/tools/ant/properties/extrapath.properties
    db/derby/code/trunk/tools/javadoc/publishedapi.ant

Modified: db/derby/code/trunk/build.xml
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/build.xml?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/build.xml (original)
+++ db/derby/code/trunk/build.xml Mon Jul 13 20:29:48 2015
@@ -2547,6 +2547,7 @@
             <pathelement location="${lucene_core}"/>
             <pathelement location="${lucene_a_co}"/>
             <pathelement location="${lucene_qp}"/>
+            <pathelement location="${json_simple}"/>
       </classpath>
     </junit>
   </target>
@@ -2742,6 +2743,7 @@
             <pathelement location="${lucene_core}"/>
             <pathelement location="${lucene_a_co}"/>
             <pathelement location="${lucene_qp}"/>
+            <pathelement location="${json_simple}"/>
       </classpath>
     </junit>
       

Modified: db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyTesting.jar.lastcontents
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyTesting.jar.lastcontents?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyTesting.jar.lastcontents (original)
+++ db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyTesting.jar.lastcontents Mon Jul 13 20:29:48 2015
@@ -1,4 +1,12 @@
 SimpleApp.class
+org.apache.derby.impl.tools.ij.SimpleCharStream.class
+org.apache.derby.impl.tools.ij.mtGrammar.class
+org.apache.derby.impl.tools.ij.mtGrammarConstants.class
+org.apache.derby.impl.tools.ij.mtGrammarTokenManager.class
+org.apache.derby.impl.tools.ij.mtTestCase.class
+org.apache.derby.impl.tools.ij.mtTestSuite.class
+org.apache.derby.impl.tools.ij.mtTester.class
+org.apache.derby.impl.tools.ij.mtTime.class
 org.apache.derbyTesting.functionTests.harness.BackgroundStreamDrainer.class
 org.apache.derbyTesting.functionTests.harness.BackgroundStreamSaver.class
 org.apache.derbyTesting.functionTests.harness.CopySuppFiles.class
@@ -353,6 +361,7 @@ org.apache.derbyTesting.functionTests.te
 org.apache.derbyTesting.functionTests.tests.lang.JitTest.class
 org.apache.derbyTesting.functionTests.tests.lang.JoinDeadlockTest.class
 org.apache.derbyTesting.functionTests.tests.lang.JoinTest.class
+org.apache.derbyTesting.functionTests.tests.lang.JsonSuite.class
 org.apache.derbyTesting.functionTests.tests.lang.LOBDB2compatibilityTest.class
 org.apache.derbyTesting.functionTests.tests.lang.LangHarnessJavaTest.class
 org.apache.derbyTesting.functionTests.tests.lang.LangProcedureTest.class
@@ -426,6 +435,7 @@ org.apache.derbyTesting.functionTests.te
 org.apache.derbyTesting.functionTests.tests.lang.SequencePermsTest.class
 org.apache.derbyTesting.functionTests.tests.lang.SequenceTest.class
 org.apache.derbyTesting.functionTests.tests.lang.ShutdownDatabaseTest.class
+org.apache.derbyTesting.functionTests.tests.lang.SimpleJsonTest.class
 org.apache.derbyTesting.functionTests.tests.lang.SimpleTest.class
 org.apache.derbyTesting.functionTests.tests.lang.SpillHashTest.class
 org.apache.derbyTesting.functionTests.tests.lang.StalePlansTest.class
@@ -1016,12 +1026,4 @@ org.apache.derbyTesting.unitTests.store.
 org.apache.derbyTesting.unitTests.store.commit_method.class
 org.apache.derbyTesting.unitTests.util.BitUtil.class
 org.apache.derbyTesting.unitTests.util.MsgTrace.class
-org.apache.derby.impl.tools.ij.SimpleCharStream.class
-org.apache.derby.impl.tools.ij.mtGrammar.class
-org.apache.derby.impl.tools.ij.mtGrammarConstants.class
-org.apache.derby.impl.tools.ij.mtGrammarTokenManager.class
-org.apache.derby.impl.tools.ij.mtTestCase.class
-org.apache.derby.impl.tools.ij.mtTestSuite.class
-org.apache.derby.impl.tools.ij.mtTester.class
-org.apache.derby.impl.tools.ij.mtTime.class
 toursdb.insertMaps.class

Modified: db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyoptionaltools.jar.lastcontents
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyoptionaltools.jar.lastcontents?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyoptionaltools.jar.lastcontents (original)
+++ db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/insane.derbyoptionaltools.jar.lastcontents Mon Jul 13 20:29:48 2015
@@ -1,5 +1,7 @@
 org.apache.derby.optional.api.LuceneIndexDescriptor.class
 org.apache.derby.optional.api.LuceneUtils.class
+org.apache.derby.optional.api.SimpleJsonUtils.class
+org.apache.derby.optional.json.SimpleJsonTool.class
 org.apache.derby.optional.lucene.DerbyIndexInput.class
 org.apache.derby.optional.lucene.DerbyIndexOutput.class
 org.apache.derby.optional.lucene.DerbyLuceneDir.class

Modified: db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyTesting.jar.lastcontents
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyTesting.jar.lastcontents?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyTesting.jar.lastcontents (original)
+++ db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyTesting.jar.lastcontents Mon Jul 13 20:29:48 2015
@@ -1,4 +1,12 @@
 SimpleApp.class
+org.apache.derby.impl.tools.ij.SimpleCharStream.class
+org.apache.derby.impl.tools.ij.mtGrammar.class
+org.apache.derby.impl.tools.ij.mtGrammarConstants.class
+org.apache.derby.impl.tools.ij.mtGrammarTokenManager.class
+org.apache.derby.impl.tools.ij.mtTestCase.class
+org.apache.derby.impl.tools.ij.mtTestSuite.class
+org.apache.derby.impl.tools.ij.mtTester.class
+org.apache.derby.impl.tools.ij.mtTime.class
 org.apache.derbyTesting.functionTests.harness.BackgroundStreamDrainer.class
 org.apache.derbyTesting.functionTests.harness.BackgroundStreamSaver.class
 org.apache.derbyTesting.functionTests.harness.CopySuppFiles.class
@@ -353,6 +361,7 @@ org.apache.derbyTesting.functionTests.te
 org.apache.derbyTesting.functionTests.tests.lang.JitTest.class
 org.apache.derbyTesting.functionTests.tests.lang.JoinDeadlockTest.class
 org.apache.derbyTesting.functionTests.tests.lang.JoinTest.class
+org.apache.derbyTesting.functionTests.tests.lang.JsonSuite.class
 org.apache.derbyTesting.functionTests.tests.lang.LOBDB2compatibilityTest.class
 org.apache.derbyTesting.functionTests.tests.lang.LangHarnessJavaTest.class
 org.apache.derbyTesting.functionTests.tests.lang.LangProcedureTest.class
@@ -426,6 +435,7 @@ org.apache.derbyTesting.functionTests.te
 org.apache.derbyTesting.functionTests.tests.lang.SequencePermsTest.class
 org.apache.derbyTesting.functionTests.tests.lang.SequenceTest.class
 org.apache.derbyTesting.functionTests.tests.lang.ShutdownDatabaseTest.class
+org.apache.derbyTesting.functionTests.tests.lang.SimpleJsonTest.class
 org.apache.derbyTesting.functionTests.tests.lang.SimpleTest.class
 org.apache.derbyTesting.functionTests.tests.lang.SpillHashTest.class
 org.apache.derbyTesting.functionTests.tests.lang.StalePlansTest.class
@@ -1016,12 +1026,4 @@ org.apache.derbyTesting.unitTests.store.
 org.apache.derbyTesting.unitTests.store.commit_method.class
 org.apache.derbyTesting.unitTests.util.BitUtil.class
 org.apache.derbyTesting.unitTests.util.MsgTrace.class
-org.apache.derby.impl.tools.ij.SimpleCharStream.class
-org.apache.derby.impl.tools.ij.mtGrammar.class
-org.apache.derby.impl.tools.ij.mtGrammarConstants.class
-org.apache.derby.impl.tools.ij.mtGrammarTokenManager.class
-org.apache.derby.impl.tools.ij.mtTestCase.class
-org.apache.derby.impl.tools.ij.mtTestSuite.class
-org.apache.derby.impl.tools.ij.mtTester.class
-org.apache.derby.impl.tools.ij.mtTime.class
 toursdb.insertMaps.class

Modified: db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyoptionaltools.jar.lastcontents
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyoptionaltools.jar.lastcontents?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyoptionaltools.jar.lastcontents (original)
+++ db/derby/code/trunk/java/build/org/apache/derbyBuild/lastgoodjarcontents/sane.derbyoptionaltools.jar.lastcontents Mon Jul 13 20:29:48 2015
@@ -1,5 +1,7 @@
 org.apache.derby.optional.api.LuceneIndexDescriptor.class
 org.apache.derby.optional.api.LuceneUtils.class
+org.apache.derby.optional.api.SimpleJsonUtils.class
+org.apache.derby.optional.json.SimpleJsonTool.class
 org.apache.derby.optional.lucene.DerbyIndexInput.class
 org.apache.derby.optional.lucene.DerbyIndexOutput.class
 org.apache.derby.optional.lucene.DerbyLuceneDir.class

Modified: db/derby/code/trunk/java/engine/org/apache/derby/catalog/Java5SystemProcedures.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/catalog/Java5SystemProcedures.java?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/catalog/Java5SystemProcedures.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/catalog/Java5SystemProcedures.java Mon Jul 13 20:29:48 2015
@@ -68,6 +68,7 @@ public  class   Java5SystemProcedures
         { "luceneSupport", "org.apache.derby.optional.lucene.LuceneSupport" },
         { "optimizerTracing", "org.apache.derby.impl.sql.compile.OptimizerTracer" },
         { "optimizerTracingViews", "org.apache.derby.impl.sql.compile.OptTraceViewer" },
+        { "simpleJson", "org.apache.derby.optional.json.SimpleJsonTool" },
     };
 
     ///////////////////////////////////////////////////////////////////////////////////

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/StaticMethodCallNode.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/StaticMethodCallNode.java?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/StaticMethodCallNode.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/StaticMethodCallNode.java Mon Jul 13 20:29:48 2015
@@ -370,6 +370,7 @@ class StaticMethodCallNode extends Metho
                 javaClassName.startsWith( "org.apache.derby." ) &&
                 !javaClassName.startsWith( "org.apache.derby.impl.tools.optional." ) &&
                 !javaClassName.startsWith( "org.apache.derby.optional.lucene." ) &&
+                !javaClassName.startsWith( "org.apache.derby.optional.json." ) &&
                 !javaClassName.startsWith( "org.apache.derby.optional.api." ) &&
                 !javaClassName.startsWith( "org.apache.derby.vti." )
                 )

Modified: db/derby/code/trunk/java/optional/build.xml
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/optional/build.xml?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/optional/build.xml (original)
+++ db/derby/code/trunk/java/optional/build.xml Mon Jul 13 20:29:48 2015
@@ -72,6 +72,7 @@
         <pathelement path="${lucene_core}"/>
         <pathelement path="${lucene_a_co}"/>
         <pathelement path="${lucene_qp}"/>
+        <pathelement path="${json_simple}"/>
       </classpath>
       <include name="${derby.dir}/${cur.dir}/**"/>
       <compilerarg value="-Xlint:unchecked"/>

Added: db/derby/code/trunk/java/optional/org/apache/derby/optional/api/SimpleJsonUtils.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/optional/org/apache/derby/optional/api/SimpleJsonUtils.java?rev=1690814&view=auto
==============================================================================
--- db/derby/code/trunk/java/optional/org/apache/derby/optional/api/SimpleJsonUtils.java (added)
+++ db/derby/code/trunk/java/optional/org/apache/derby/optional/api/SimpleJsonUtils.java Mon Jul 13 20:29:48 2015
@@ -0,0 +1,184 @@
+/*
+
+   Derby - Class org.apache.derby.optional.api.SimpleJsonUtils
+
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
+ */
+
+package org.apache.derby.optional.api;
+
+import java.sql.Blob;
+import java.sql.Clob;
+import java.sql.Connection;
+import java.sql.DriverManager;
+import java.sql.PreparedStatement;
+import java.sql.ResultSet;
+import java.sql.ResultSetMetaData;
+import java.sql.SQLException;
+
+import org.json.simple.JSONArray;
+import org.json.simple.JSONObject;
+
+import org.apache.derby.iapi.util.StringUtil;
+
+/**
+ * <p>
+ * Utility methods for simple JSON support.
+ * </p>
+ */
+public abstract class SimpleJsonUtils
+{
+    /////////////////////////////////////////////////////////////////
+    //
+    //  CONSTANTS
+    //
+    /////////////////////////////////////////////////////////////////
+
+    /////////////////////////////////////////////////////////////////
+    //
+    //  STATE
+    //
+    /////////////////////////////////////////////////////////////////
+
+    /////////////////////////////////////////////////////////////////
+    //
+    //  PUBLIC BEHAVIOR
+    //
+    /////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Pack a ResultSet into a JSONArray. This method could be called
+     * client-side on any query result from any DBMS. Each row is
+     * converted into a JSONObject whose keys are the corresponding
+     * column names from the ResultSet.
+     * Closes the ResultSet once it has been drained. Datatypes map
+     * to JSON values as follows:
+     * </p>
+     *
+     * <ul>
+     * <li><i>NULL</i> - The JSON null literal.</li>
+     * <li><i>SMALLINT, INT, BIGINT</i> - JSON integer values.</li>
+     * <li><i>DOUBLE, FLOAT, REAL, DECIMAL, NUMERIC</i> - JSON floating point values.</li>
+     * <li><i>CHAR, VARCHAR, LONG VARCHAR, CLOB</i> - JSON string values.</li>
+     * <li><i>BLOB, VARCHAR FOR BIT DATA, LONG VARCHAR FOR BIT DATA</i> - The
+     * byte array is turned into a hex string (2 hex digits per byte) and the
+     * result is returned as a JSON string.</li>
+     * <li><i>All other types</i> - Converted to JSON
+     * string values via their toString() methods.</li>
+     * </ul>
+     */
+    @SuppressWarnings("unchecked")
+    public  static  JSONArray   toJSON( ResultSet rs )
+        throws SQLException
+    {
+        ResultSetMetaData   rsmd = rs.getMetaData();
+        int                 columnCount = rsmd.getColumnCount();
+        JSONArray           result = new JSONArray();
+
+        try {
+            while( rs.next() )
+            {
+                JSONObject  row = new JSONObject();
+
+                for ( int i = 1; i <= columnCount; i++ )
+                {
+                    String  keyName = rsmd.getColumnName( i );
+                    Object  value = getLegalJsonValue( rs.getObject( i ) );
+
+                    row.put( keyName, value );
+                }
+
+                result.add( row );
+            }
+        }
+        finally
+        {
+            if ( rs != null )
+            {
+                rs.close();
+            }
+        }
+
+        return result;
+    }
+
+    /////////////////////////////////////////////////////////////////
+    //
+    //  MINIONS
+    //
+    /////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Turns an object into something which is a legal JSON value.
+     * </p>
+     */
+    private static  Object  getLegalJsonValue( Object obj )
+        throws SQLException
+    {
+        if (
+            (obj == null) ||
+            (obj instanceof Long) ||
+            (obj instanceof Double) ||
+            (obj instanceof Boolean) ||
+            (obj instanceof String) ||
+            (obj instanceof JSONObject) ||
+            (obj instanceof JSONArray)
+            )
+        {
+            return obj;
+        }
+        // other exact integers
+        else if (
+                 (obj instanceof Byte) ||
+                 (obj instanceof Short) ||
+                 (obj instanceof Integer)
+                 )
+        {
+            return ((Number) obj).longValue();
+        }
+        // all other numbers, including BigDecimal
+        else if (obj instanceof Number) { return ((Number) obj).doubleValue(); }
+        else if (obj instanceof Clob)
+        {
+            Clob    clob = (Clob) obj;
+            return clob.getSubString( 1, (int) clob.length() );
+        }
+        else if (obj instanceof Blob)
+        {
+            Blob    blob = (Blob) obj;
+            return formatBytes( blob.getBytes( 1, (int) blob.length() ) );
+        }
+        if (obj instanceof byte[])
+        {
+            return formatBytes( (byte[]) obj );
+        }
+        // catch-all
+        else { return obj.toString(); }
+    }
+
+    private static  String  formatBytes( byte[] bytes )
+    {
+        return StringUtil.toHexString( bytes, 0, bytes.length );
+    }
+
+    private static  Connection  getDerbyConnection() throws SQLException
+    {
+        return DriverManager.getConnection( "jdbc:default:connection" );
+    }
+}

Propchange: db/derby/code/trunk/java/optional/org/apache/derby/optional/api/SimpleJsonUtils.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: db/derby/code/trunk/java/optional/org/apache/derby/optional/json/SimpleJsonTool.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/optional/org/apache/derby/optional/json/SimpleJsonTool.java?rev=1690814&view=auto
==============================================================================
--- db/derby/code/trunk/java/optional/org/apache/derby/optional/json/SimpleJsonTool.java (added)
+++ db/derby/code/trunk/java/optional/org/apache/derby/optional/json/SimpleJsonTool.java Mon Jul 13 20:29:48 2015
@@ -0,0 +1,259 @@
+/*
+
+   Derby - Class org.apache.derby.optional.json.SimpleJsonTool
+
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
+ */
+
+package org.apache.derby.optional.json;
+
+import java.sql.Connection;
+import java.sql.DatabaseMetaData;
+import java.sql.DriverManager;
+import java.sql.PreparedStatement;
+import java.sql.ResultSet;
+import java.sql.SQLException;
+
+import org.json.simple.JSONArray;
+
+import org.apache.derby.iapi.sql.dictionary.OptionalTool;
+import org.apache.derby.iapi.tools.i18n.LocalizedResource;
+import org.apache.derby.iapi.util.IdUtil;
+import org.apache.derby.iapi.util.StringUtil;
+import org.apache.derby.optional.api.SimpleJsonUtils;
+
+/**
+ * <p>
+ * OptionalTool which adds a function for turning a query result
+ * into a JSON array. Each cell in the array is a row. Each row
+ * has key/value pairs for all columns returned by the query.
+ * This tool binds a user-defined type to the simple-json JSONArray
+ * class.
+ * </p>
+ */
+public	class   SimpleJsonTool  implements OptionalTool
+{
+    ////////////////////////////////////////////////////////////////////////
+    //
+    //	CONSTANTS
+    //
+    ////////////////////////////////////////////////////////////////////////
+
+    ////////////////////////////////////////////////////////////////////////
+    //
+    //	STATE
+    //
+    ////////////////////////////////////////////////////////////////////////
+
+    ////////////////////////////////////////////////////////////////////////
+    //
+    //	CONSTRUCTOR
+    //
+    ////////////////////////////////////////////////////////////////////////
+
+    /** 0-arg constructor required by the OptionalTool contract */
+    public  SimpleJsonTool() {}
+
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // OptionalTool BEHAVIOR
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Binds a UDT to JSONArray and creates a function to turn a query result
+     * into a JSONArray. There are no parameters to this method.
+     * </p>
+     */
+    public  void    loadTool( String... configurationParameters )
+        throws SQLException
+    {
+        if ( (configurationParameters != null) && (configurationParameters.length != 0) )
+        {
+            throw wrap( LocalizedResource.getMessage( "OT_BadLoadUnloadArgs" ) );
+        }
+
+        Connection          derbyConn = getDerbyConnection();
+
+        createUDT( derbyConn );
+        createFunction( derbyConn );
+    }
+
+    /**
+     * <p>
+     * Removes the function and UDT created by loadTool().
+     * </p>
+     * </ul>
+     */
+    public  void    unloadTool( String... configurationParameters )
+        throws SQLException
+    {
+        if ( (configurationParameters != null) && (configurationParameters.length != 0) )
+        {
+            throw wrap( LocalizedResource.getMessage( "OT_BadLoadUnloadArgs" ) );
+        }
+
+        Connection          derbyConn = getDerbyConnection();
+
+        dropFunction( derbyConn );
+        dropUDT( derbyConn );
+    }
+
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // SQL FUNCTIONS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Compile a query (with optional ? parameters) and pack the results
+     * into a JSONArray. This is the entry point which the simpleJson
+     * tool binds to the function name "toJSON".
+     * </p>
+     */
+    public  static  JSONArray   toJSON
+        (
+         String queryString,
+         String... queryArgs
+         )
+        throws SQLException
+    {
+        PreparedStatement   ps = null;
+
+        try {
+            Connection  conn = getDerbyConnection();
+            
+            ps = conn.prepareStatement( queryString );
+
+            if ( queryArgs != null )
+            {
+                for ( int i = 0; i < queryArgs.length; i++  )
+                {
+                    ps.setString( i + 1, queryArgs[ i ] );
+                }
+            }
+
+            ResultSet   rs = ps.executeQuery();
+
+            return SimpleJsonUtils.toJSON( rs );
+        }
+        finally
+        {
+            if ( ps != null )
+            {
+                ps.close();
+            }
+        }
+    }
+    
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // (UN)REGISTRATION MINIONS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    private void    createUDT
+        (
+         Connection     derbyConn
+        )
+        throws SQLException
+    {
+        String  createString =
+            "create type JSONArray external name 'org.json.simple.JSONArray' language java";
+        
+        executeDDL( derbyConn, createString );
+    }
+
+    private void    dropUDT
+        (
+         Connection     derbyConn
+        )
+        throws SQLException
+    {
+        String  createString =
+            "drop type JSONArray restrict";
+        
+        executeDDL( derbyConn, createString );
+    }
+
+    private void    createFunction
+        (
+         Connection     derbyConn
+        )
+        throws SQLException
+    {
+        String  createString =
+            "create function toJSON" +
+            "\n(" +
+            "\n\tqueryString varchar( 32672 )," +
+            "\n\tqueryArgs varchar( 32672 ) ..." +
+            "\n)\nreturns JSONArray\n" +
+            "\nlanguage java parameter style derby reads sql data" +
+            "\nexternal name 'org.apache.derby.optional.json.SimpleJsonTool.toJSON'";
+
+        executeDDL( derbyConn, createString );
+    }
+
+    private void    dropFunction
+        (
+         Connection     derbyConn
+        )
+        throws SQLException
+    {
+        String  createString =
+            "drop function toJSON";
+        
+        executeDDL( derbyConn, createString );
+    }
+
+    ////////////////////////////////////////////////////////////////////////
+    //
+    //	SQL MINIONS
+    //
+    ////////////////////////////////////////////////////////////////////////
+
+    private void    executeDDL
+        ( Connection conn, String text )
+        throws SQLException
+    {
+        PreparedStatement   ddl = prepareStatement( conn, text );
+        ddl.execute();
+        ddl.close();
+    }
+    
+    private PreparedStatement   prepareStatement
+        ( Connection conn, String text )
+        throws SQLException
+    {
+        return conn.prepareStatement( text );
+    }
+
+    private SQLException    wrap( String errorMessage )
+    {
+        String  sqlState = org.apache.derby.shared.common.reference.SQLState.JAVA_EXCEPTION.substring( 0, 5 );
+
+        return new SQLException( errorMessage, sqlState );
+    }
+
+    private static  Connection  getDerbyConnection() throws SQLException
+    {
+        return DriverManager.getConnection( "jdbc:default:connection" );
+    }
+
+}

Propchange: db/derby/code/trunk/java/optional/org/apache/derby/optional/json/SimpleJsonTool.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/JsonSuite.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/JsonSuite.java?rev=1690814&view=auto
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/JsonSuite.java (added)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/JsonSuite.java Mon Jul 13 20:29:48 2015
@@ -0,0 +1,71 @@
+/*
+
+   Derby - Class org.apache.derbyTesting.functionTests.tests.lang.JsonSuite
+
+       Licensed to the Apache Software Foundation (ASF) under one
+       or more contributor license agreements.  See the NOTICE file
+       distributed with this work for additional information
+       regarding copyright ownership.  The ASF licenses this file
+       to you under the Apache License, Version 2.0 (the
+       "License"); you may not use this file except in compliance
+       with the License.  You may obtain a copy of the License at
+
+         http://www.apache.org/licenses/LICENSE-2.0
+
+       Unless required by applicable law or agreed to in writing,
+       software distributed under the License is distributed on an
+       "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+       KIND, either express or implied.  See the License for the
+       specific language governing permissions and limitations
+       under the License
+*/
+package org.apache.derbyTesting.functionTests.tests.lang;
+
+import java.util.Properties;
+import junit.framework.Test;
+import org.apache.derbyTesting.junit.BaseTestCase;
+import org.apache.derbyTesting.junit.BaseTestSuite;
+import org.apache.derbyTesting.junit.JDBC;
+import org.apache.derbyTesting.junit.TestConfiguration;
+
+/**
+ * Suite holding all of the tests for the optional simple json support.
+ *
+ */
+public class JsonSuite extends BaseTestCase
+{
+
+	/**
+	 * Use suite method instead.
+	 */
+	private JsonSuite(String name) { super(name); }
+
+	public static Test suite()
+    {
+        BaseTestSuite suite = new BaseTestSuite("JsonSuite");
+        Properties  properties = TestConfiguration.getSystemProperties();
+        
+        //
+        // If we're told to omit the json tests, make sure
+        // that the json jar file isn't on the classpath.
+        //
+        if ( getBooleanProperty( properties, TestConfiguration.KEY_OMIT_JSON ) )
+        {
+            assertFalse
+                ( "The json-simple jar file should not be on the classpath!", JDBC.HAVE_JSON_SIMPLE );
+        }
+        else
+        {
+            suite.addTest(SimpleJsonTest.suite());
+        }
+
+        return suite;
+	}
+
+    /** Return the boolean value of a system property */
+    private static  boolean getBooleanProperty( Properties properties, String key )
+    {
+        return Boolean.valueOf( properties.getProperty( key ) ).booleanValue();
+    }
+
+}

Propchange: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/JsonSuite.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SimpleJsonTest.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SimpleJsonTest.java?rev=1690814&view=auto
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SimpleJsonTest.java (added)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SimpleJsonTest.java Mon Jul 13 20:29:48 2015
@@ -0,0 +1,599 @@
+/**
+ *  Derby - Class org.apache.derbyTesting.functionTests.tests.lang.SimpleJsonTest
+ *  
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.derbyTesting.functionTests.tests.lang;
+
+import java.sql.Connection;
+import java.util.Arrays;
+
+import junit.framework.Test;
+import org.apache.derbyTesting.junit.BaseJDBCTestCase;
+import org.apache.derbyTesting.junit.BaseTestSuite;
+import org.apache.derbyTesting.junit.JDBC;
+import org.apache.derbyTesting.junit.TestConfiguration;
+
+import org.json.simple.JSONArray;
+import org.json.simple.JSONObject;
+
+/**
+ * <p>
+ * Basic test of the optional tool which provides JSON support functions
+ * which use the simple json library from https://code.google.com/p/json-simple/.
+ * </p>
+ */
+public class SimpleJsonTest extends BaseJDBCTestCase
+{
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // CONSTANTS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    private static  final   String  TAB = "  ";
+    private static  final   String  USER_ERROR = "38000";
+
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // CONSTRUCTORS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+	public SimpleJsonTest(String name) {
+		super(name);
+	}
+	
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // JUnit MACHINERY
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+    
+	public static Test suite()
+    {
+        BaseTestSuite suite = new BaseTestSuite("SimpleJsonTest");
+
+        suite.addTest( TestConfiguration.defaultSuite( SimpleJsonTest.class ) );
+
+        return suite;
+	}
+	
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // JUnit TESTS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+    
+	public void testBasic_001() throws Exception
+    {
+        Connection  conn = getConnection();
+
+        // create the json support types and functions
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', true )" );
+
+        createSchema_001( conn );
+
+        assertResults
+            (
+             conn,
+             "values prettyPrint( toJSON( " +
+             "'select * from thermostatReadings order by \"id\", \"sampleTime\"' ) )",
+             new String[][]
+             {
+                 {
+                     "[\n" +
+                     "  {\n" +
+                     "    \"fanOn\" : false, \n" +
+                     "    \"id\" : 1, \n" +
+                     "    \"sampleTime\" : \"2015-07-08 04:03:20.0\", \n" +
+                     "    \"temperature\" : 65.5\n" +
+                     "  }, \n" +
+                     "  {\n" +
+                     "    \"fanOn\" : true, \n" +
+                     "    \"id\" : 1, \n" +
+                     "    \"sampleTime\" : \"2015-07-08 13:03:20.0\", \n" +
+                     "    \"temperature\" : 70.1\n" +
+                     "  }, \n" +
+                     "  {\n" +
+                     "    \"fanOn\" : false, \n" +
+                     "    \"id\" : 2, \n" +
+                     "    \"sampleTime\" : \"2015-07-08 03:03:20.0\", \n" +
+                     "    \"temperature\" : 64.5\n" +
+                     "  }, \n" +
+                     "  {\n" +
+                     "    \"fanOn\" : true, \n" +
+                     "    \"id\" : 2, \n" +
+                     "    \"sampleTime\" : \"2015-07-08 16:03:20.0\", \n" +
+                     "    \"temperature\" : 72.1\n" +
+                     "  }\n" +
+                     "]"
+                 }
+             },
+             true
+             );
+
+        assertResults
+            (
+             conn,
+             "values prettyPrint( toJSON( 'select \"id\", max( \"temperature\" ) \"maxTemp\" from thermostatReadings group by \"id\"' ) )",
+             new String[][]
+             {
+                 {
+                     "[\n" +
+                     "  {\n" +
+                     "    \"id\" : 1, \n" +
+                     "    \"maxTemp\" : 70.1\n" +
+                     "  }, \n" +
+                     "  {\n" +
+                     "    \"id\" : 2, \n" +
+                     "    \"maxTemp\" : 72.1\n" +
+                     "  }\n" +
+                     "]"
+                 }
+             },
+             true
+             );
+
+        assertResults
+            (
+             conn,
+             "values prettyPrint( toJSON( 'select \"id\", max( \"temperature\" ) \"maxTemp\" from thermostatReadings where \"id\" = ? group by \"id\"', '2' ) )",
+             new String[][]
+             {
+                 {
+                     "[\n" +
+                     "  {\n" +
+                     "    \"id\" : 2, \n" +
+                     "    \"maxTemp\" : 72.1\n" +
+                     "  }\n" +
+                     "]"
+                 }
+             },
+             true
+             );
+
+        dropSchema_001( conn );
+        
+        // drop the json support types and functions
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', false )" );
+	}
+    private void    createSchema_001( Connection conn ) throws Exception
+    {
+        goodStatement
+            (
+             conn,
+             "create table thermostatReadings\n" +
+             "(\n" +
+             "\"id\" int,\n" +
+             "\"temperature\" double,\n" +
+             "\"fanOn\" boolean,\n" +
+             "\"sampleTime\" timestamp,\n" +
+             "primary key( \"id\", \"sampleTime\" )\n" +
+             ")\n"
+             );
+
+        goodStatement
+            (
+             conn,
+             "insert into thermostatReadings values\n" +
+             "( 1, 65.5, false, timestamp( '2015-07-08 04:03:20') ),\n" +
+             "( 1, 70.1, true, timestamp( '2015-07-08 13:03:20') ),\n" +
+             "( 2, 64.5, false, timestamp( '2015-07-08 03:03:20') ),\n" +
+             "( 2, 72.1, true, timestamp( '2015-07-08 16:03:20') )\n"
+             );
+        
+        goodStatement
+            (
+             conn,
+             "create function prettyPrint( doc JSONArray ) returns varchar( 32672 )\n" +
+             "language java parameter style java no sql\n" +
+             "external name '" + getClass().getName() + ".prettyPrint'\n"
+             );
+    }
+    private void    dropSchema_001( Connection conn ) throws Exception
+    {
+        goodStatement( conn, "drop function prettyPrint" );
+        goodStatement( conn, "drop table thermostatReadings" );
+    }
+    
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Test the jsonification of Derby's datatypes.
+     * </p>
+     */
+	public void testDatatypes_002() throws Exception
+    {
+        Connection  conn = getConnection();
+
+        // create the json support types and functions
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', true )" );
+
+        createSchema_002( conn );
+
+        assertResults
+            (
+             conn,
+             "values( prettyPrint( toJSON( 'select * from all_types order by key_col' ) ) )",
+             new String[][]
+             {
+                 {
+                     "[\n" +
+                     "  {\n" +
+                     "    \"BIGINT_COL\" : 0, \n" +
+                     "    \"BLOB_COL\" : \"01\", \n" +
+                     "    \"CHAR_COL\" : \"0         \", \n" +
+                     "    \"CHAR_FOR_BIT_DATA_COL\" : \"de202020202020202020\", \n" +
+                     "    \"CLOB_COL\" : \"0\", \n" +
+                     "    \"DATE_COL\" : \"1994-02-23\", \n" +
+                     "    \"DECIMAL_COL\" : 0.0, \n" +
+                     "    \"DOUBLE_COL\" : 0.0, \n" +
+                     "    \"INT_COL\" : 0, \n" +
+                     "    \"JSON_ARRAY_COL\" : [\n" +
+                     "      {\n" +
+                     "        \"A\" : 1, \n" +
+                     "        \"B\" : true\n" +
+                     "      }, \n" +
+                     "      {\n" +
+                     "        \"A\" : 2, \n" +
+                     "        \"B\" : false\n" +
+                     "      }\n" +
+                     "    ], \n" +
+                     "    \"KEY_COL\" : 0, \n" +
+                     "    \"LONG_VARCHAR_COL\" : \"0\", \n" +
+                     "    \"LONG_VARCHAR_FOR_BIT_DATA_COL\" : \"de\", \n" +
+                     "    \"NUMERIC_COL\" : 0.0, \n" +
+                     "    \"PRICE_COL\" : \"Price( USD, 9.99000, 2009-10-16 14:24:43.0 )\", \n" +
+                     "    \"REAL_COL\" : 0.0, \n" +
+                     "    \"SMALLINT_COL\" : 0, \n" +
+                     "    \"TIMESTAMP_COL\" : \"1962-09-23 03:23:34.234\", \n" +
+                     "    \"TIME_COL\" : \"15:09:02\", \n" +
+                     "    \"VARCHAR_COL\" : \"0\", \n" +
+                     "    \"VARCHAR_FOR_BIT_DATA_COL\" : \"de\"\n" +
+                     "  }, \n" +
+                     "  {\n" +
+                     "    \"BIGINT_COL\" : null, \n" +
+                     "    \"BLOB_COL\" : null, \n" +
+                     "    \"CHAR_COL\" : null, \n" +
+                     "    \"CHAR_FOR_BIT_DATA_COL\" : null, \n" +
+                     "    \"CLOB_COL\" : null, \n" +
+                     "    \"DATE_COL\" : null, \n" +
+                     "    \"DECIMAL_COL\" : null, \n" +
+                     "    \"DOUBLE_COL\" : null, \n" +
+                     "    \"INT_COL\" : null, \n" +
+                     "    \"JSON_ARRAY_COL\" : null, \n" +
+                     "    \"KEY_COL\" : 1, \n" +
+                     "    \"LONG_VARCHAR_COL\" : null, \n" +
+                     "    \"LONG_VARCHAR_FOR_BIT_DATA_COL\" : null, \n" +
+                     "    \"NUMERIC_COL\" : null, \n" +
+                     "    \"PRICE_COL\" : null, \n" +
+                     "    \"REAL_COL\" : null, \n" +
+                     "    \"SMALLINT_COL\" : null, \n" +
+                     "    \"TIMESTAMP_COL\" : null, \n" +
+                     "    \"TIME_COL\" : null, \n" +
+                     "    \"VARCHAR_COL\" : null, \n" +
+                     "    \"VARCHAR_FOR_BIT_DATA_COL\" : null\n" +
+                     "  }\n" +
+                     "]"                                                                                                     }
+             },
+             true
+             );
+
+        dropSchema_002( conn );
+
+        // drop the json support types and functions
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', false )" );
+    }
+    private void createSchema_002( Connection conn ) throws Exception
+    {
+        goodStatement
+            (
+             conn,
+             "create type Price external name 'org.apache.derbyTesting.functionTests.tests.lang.Price' language java"
+             );
+        goodStatement
+            (
+             conn,
+             "create function makePrice( currencyCode char( 3 ), amount decimal( 31, 5 ), timeInstant Timestamp )\n" +
+             "returns Price language java parameter style java no sql\n" +
+             "external name 'org.apache.derbyTesting.functionTests.tests.lang.Price.makePrice'\n"
+             );
+        goodStatement
+            (
+             conn,
+             "create function makeSimpleBlob( ) returns blob\n" +
+             "language java parameter style java no sql deterministic\n" +
+             "external name 'org.apache.derbyTesting.functionTests.tests.lang.BooleanValuesTest.makeSimpleBlob'\n"
+             );
+        goodStatement
+            (
+             conn,
+             "create table dummy( a int, b boolean )"
+             );
+        goodStatement
+            (
+             conn,
+             "insert into dummy values ( 1, true ), ( 2, false )"
+             );
+        goodStatement
+            (
+             conn,
+             "create table all_types\n" +
+             "(\n" +
+             "    key_col int,\n" +
+             "    bigint_col  BIGINT,\n" +
+             "    blob_col  BLOB(2147483647),\n" +
+             "    char_col  CHAR(10),\n" +
+             "    char_for_bit_data_col  CHAR (10) FOR BIT DATA,\n" +
+             "    clob_col  CLOB(2147483647),\n" +
+             "    date_col  DATE,\n" +
+             "    decimal_col  DECIMAL(5,2),\n" +
+             "    real_col  REAL,\n" +
+             "    double_col  DOUBLE,\n" +
+             "    int_col  INTEGER,\n" +
+             "    long_varchar_col  LONG VARCHAR,\n" +
+             "    long_varchar_for_bit_data_col  LONG VARCHAR FOR BIT DATA,\n" +
+             "    numeric_col  NUMERIC(5,2),\n" +
+             "    smallint_col  SMALLINT,\n" +
+             "    time_col  TIME,\n" +
+             "    timestamp_col  TIMESTAMP,\n" +
+             "    varchar_col  VARCHAR(10),\n" +
+             "    varchar_for_bit_data_col  VARCHAR (10) FOR BIT DATA,\n" +
+             "    price_col price,\n" +
+             "    json_array_col jsonArray\n" +
+             ")\n"
+             );
+        goodStatement
+            (
+             conn,
+             "insert into all_types( key_col ) values ( 1 )"
+             );
+        goodStatement
+            (
+             conn,
+             "insert into all_types\n" +
+             "(\n" +
+             "    key_col,\n" +
+             "    bigint_col,\n" +
+             "    blob_col,\n" +
+             "    char_col,\n" +
+             "    char_for_bit_data_col,\n" +
+             "    clob_col,\n" +
+             "    date_col,\n" +
+             "    decimal_col,\n" +
+             "    real_col,\n" +
+             "    double_col,\n" +
+             "    int_col,\n" +
+             "    long_varchar_col,\n" +
+             "    long_varchar_for_bit_data_col,\n" +
+             "    numeric_col,\n" +
+             "    smallint_col,\n" +
+             "    time_col,\n" +
+             "    timestamp_col,\n" +
+             "    varchar_col,\n" +
+             "    varchar_for_bit_data_col,\n" +
+             "    price_col,\n" +
+             "    json_array_col\n" +
+             ")\n" +
+             "values\n" +
+             "(\n" +
+             "    0,\n" +
+             "    0,\n" +
+             "    makeSimpleBlob(),\n" +
+             "    '0',\n" +
+             "    X'DE',\n" +
+             "    '0',\n" +
+             "    date('1994-02-23'),\n" +
+             "    0.00,\n" +
+             "    0.0,\n" +
+             "    0.0,\n" +
+             "    0,\n" +
+             "    '0',\n" +
+             "    X'DE',\n" +
+             "    0.00,\n" +
+             "    0,\n" +
+             "    time('15:09:02'),\n" +
+             "    timestamp('1962-09-23 03:23:34.234'),\n" +
+             "    '0',\n" +
+             "    X'DE',\n" +
+             "    makePrice( 'USD', cast( 9.99 as decimal( 31, 5 ) ), timestamp('2009-10-16 14:24:43') ),\n" +
+             "    toJSON( 'select * from dummy order by a' ) \n" +
+             ")\n"
+             );
+        goodStatement
+            (
+             conn,
+             "create function prettyPrint( doc JSONArray ) returns varchar( 32672 )\n" +
+             "language java parameter style java no sql\n" +
+             "external name 'org.apache.derbyTesting.functionTests.tests.lang.SimpleJsonTest.prettyPrint'\n"
+             );
+    }
+    private void dropSchema_002( Connection conn ) throws Exception
+    {
+        goodStatement
+            (
+             conn,
+             "drop function makePrice"
+             );
+        goodStatement
+            (
+             conn,
+             "drop function makeSimpleBlob"
+             );
+        goodStatement
+            (
+             conn,
+             "drop table all_types"
+             );
+        goodStatement
+            (
+             conn,
+             "drop type price restrict"
+             );
+        goodStatement
+            (
+             conn,
+             "drop function prettyPrint"
+             );
+
+    }
+
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Test errors.
+     * </p>
+     */
+	public void testNegative_003() throws Exception
+    {
+        Connection  conn = getConnection();
+
+        // can't load the tool redundantly
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', true )" );
+
+        expectExecutionError
+            (
+             conn,
+             USER_ERROR,
+             "call syscs_util.syscs_register_tool( 'simpleJson', true )"
+             );
+        
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', false )" );
+
+        // can't unload the tool redundantly
+        expectExecutionError
+            (
+             conn,
+             USER_ERROR,
+             "call syscs_util.syscs_register_tool( 'simpleJson', false )"
+             );
+
+        // need to specify all ? parameters
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', true )" );
+
+        expectExecutionError
+            (
+             conn,
+             USER_ERROR,
+             "values( toJSON( 'select * from sys.systables where tablename = ?' ) )"
+             );
+
+        goodStatement( conn, "call syscs_util.syscs_register_tool( 'simpleJson', false )" );
+    }
+
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // FUNCTIONS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    /**
+     * <p>
+     * Pretty-print a JSONArray.
+     * </p>
+     */
+    public static String prettyPrint( JSONArray array )
+    {
+        StringBuilder   buffer = new StringBuilder();
+
+        prettyPrintArray( buffer, 0, array );
+        
+        return buffer.toString();
+    }
+
+    private static  void    prettyPrintArray
+        (
+         StringBuilder buffer,
+         int indentLevel,
+         JSONArray array
+         )
+    {
+        buffer.append( "[" );
+        int cellCount = array.size();
+        if ( cellCount > 0 )
+        {
+            for ( int i = 0; i < cellCount; i++ )
+            {
+                if ( i > 0 ) { buffer.append( ", " ); }
+                indent( buffer, indentLevel + 1 );
+                prettyPrint( buffer, indentLevel + 1, array.get( i ) );
+            }
+            indent( buffer, indentLevel );
+        }
+        buffer.append( "]" );
+    }
+
+    private static  void    prettyPrintObject
+        (
+         StringBuilder buffer,
+         int indentLevel,
+         JSONObject obj
+         )
+    {
+        buffer.append( "{" );
+        int keyCount = obj.size();
+        if ( keyCount > 0 )
+        {
+            // alphabetize the keys
+            Object[]    keys = obj.keySet().toArray();
+            Arrays.sort( keys );
+            for ( int i = 0; i < keyCount; i++ )
+            {
+                Object  key = keys[ i ];
+                if ( i > 0 ) { buffer.append( ", " ); }
+                indent( buffer, indentLevel + 1 );
+                buffer.append( doubleQuote( (String) key ) );
+                buffer.append( " : " );
+                prettyPrint( buffer, indentLevel + 1, obj.get( key ) );
+            }
+            indent( buffer, indentLevel );
+        }
+        buffer.append( "}" );
+    }
+
+    private static void prettyPrint
+        (
+         StringBuilder buffer,
+         int indentLevel,
+         Object obj
+         )
+    {
+        if ( obj == null ) { buffer.append( "null" ); }
+        else if ( obj instanceof JSONArray )
+        { prettyPrintArray( buffer, indentLevel, (JSONArray) obj ); }
+        else if ( obj instanceof JSONObject )
+        { prettyPrintObject( buffer, indentLevel, (JSONObject) obj ); }
+        else if ( (obj instanceof Number) || (obj instanceof Boolean) )
+        { buffer.append( obj.toString() ); }
+        else { buffer.append( doubleQuote( obj.toString() ) ); }
+    }
+
+    private static  void indent( StringBuilder buffer, int indentLevel )
+    {
+        buffer.append( "\n" );
+        for ( int i = 0; i < indentLevel; i++ ) { buffer.append( TAB ); }
+    }
+
+    private static  String  doubleQuote( String raw )
+    {
+        return "\"" + raw + "\"";
+    }
+}

Propchange: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SimpleJsonTest.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/_Suite.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/_Suite.java?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/_Suite.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/_Suite.java Mon Jul 13 20:29:48 2015
@@ -257,6 +257,7 @@ public class _Suite extends BaseTestCase
         suite.addTest(ForeignKeysDeferrableTest.suite());
         suite.addTest(DB2IsolationLevelsTest.suite());
         suite.addTest(LuceneSuite.suite());
+        suite.addTest(JsonSuite.suite());
         suite.addTest(ConsistencyCheckerTest.suite());
         suite.addTest(Derby5866TriggerOrderTest.suite());
         suite.addTest(NoDBInternalsPermissionTest.suite());

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/build.xml
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/build.xml?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/build.xml (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/build.xml Mon Jul 13 20:29:48 2015
@@ -85,6 +85,7 @@
         <pathelement path="${lucene_core}"/>
         <pathelement path="${lucene_a_co}"/>
         <pathelement path="${lucene_qp}"/>
+        <pathelement path="${json_simple}"/>
       </classpath>
       <include name="${this.dir}/*.java"/>
       <compilerarg value="-Xlint"/>

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/JDBC.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/JDBC.java?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/JDBC.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/JDBC.java Mon Jul 13 20:29:48 2015
@@ -126,6 +126,10 @@ public class JDBC {
     public  static  final   boolean HAVE_LUCENE_QUERYPARSER =
         haveClass( "org.apache.lucene.queryparser.surround.parser.QueryParser" );
 
+    /** Is the json-simple core jar file on the classpath */
+    public  static  final   boolean HAVE_JSON_SIMPLE =
+        haveClass( "org.json.simple.JSONArray" );
+
     /**
      * Does java.sql.ResultSet implement java.lang.AutoCloseable?
      * Indicates JDBC 4.1.

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/TestConfiguration.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/TestConfiguration.java?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/TestConfiguration.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/junit/TestConfiguration.java Mon Jul 13 20:29:48 2015
@@ -117,6 +117,7 @@ public final class TestConfiguration {
     private final static String KEY_LOGIN_TIMEOUT = "derby.tests.login.timeout";    
     private final static String KEY_TRACE = "derby.tests.trace";
     public  final static String KEY_OMIT_LUCENE = "derby.tests.omitLucene";
+    public  final static String KEY_OMIT_JSON = "derby.tests.omitJson";
 
     /**
      * derby.tests.stopAfterFirstFail - debugging property to exit after 

Modified: db/derby/code/trunk/tools/ant/properties/extrapath.properties
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/tools/ant/properties/extrapath.properties?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/tools/ant/properties/extrapath.properties (original)
+++ db/derby/code/trunk/tools/ant/properties/extrapath.properties Mon Jul 13 20:29:48 2015
@@ -32,8 +32,9 @@ emma_ant=${javatools.dir}/emma_ant.jar
 lucene_core=${javatools.dir}/lucene-core.jar
 lucene_a_co=${javatools.dir}/lucene-analyzers-common.jar
 lucene_qp=${javatools.dir}/lucene-queryparser.jar
+json_simple=${javatools.dir}/json_simple-1.1.jar
 
 #
 # Base JavaDoc collection, used for both product and test JavaDocs.
 #
-jars.javadoc=${osgi};${oro};${servlet24}:${lucene_core}:${lucene_a_co}:${lucene_qp}
+jars.javadoc=${osgi};${oro};${servlet24}:${lucene_core}:${lucene_a_co}:${lucene_qp}:${json_simple}

Added: db/derby/code/trunk/tools/java/json_simple-1.1.jar
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/tools/java/json_simple-1.1.jar?rev=1690814&view=auto
==============================================================================
Binary file - no diff available.

Propchange: db/derby/code/trunk/tools/java/json_simple-1.1.jar
------------------------------------------------------------------------------
    svn:mime-type = application/octet-stream

Modified: db/derby/code/trunk/tools/javadoc/publishedapi.ant
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/tools/javadoc/publishedapi.ant?rev=1690814&r1=1690813&r2=1690814&view=diff
==============================================================================
--- db/derby/code/trunk/tools/javadoc/publishedapi.ant (original)
+++ db/derby/code/trunk/tools/javadoc/publishedapi.ant Mon Jul 13 20:29:48 2015
@@ -81,4 +81,5 @@ org/apache/derby/security/SystemPermissi
 
 org/apache/derby/optional/api/LuceneIndexDescriptor.java
 org/apache/derby/optional/api/LuceneUtils.java
+org/apache/derby/optional/api/SimpleJsonUtils.java
 

Added: db/derby/code/trunk/tools/release/notices/simpleJson.txt
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/tools/release/notices/simpleJson.txt?rev=1690814&view=auto
==============================================================================
--- db/derby/code/trunk/tools/release/notices/simpleJson.txt (added)
+++ db/derby/code/trunk/tools/release/notices/simpleJson.txt Mon Jul 13 20:29:48 2015
@@ -0,0 +1,4 @@
+The Derby build relies on a jar file supplied by the JSON Simple
+project, hosted at https://code.google.com/p/json-simple/.
+The JSON simple jar file is licensed under the Apache 2.0 License.
+No other notice covers that jar file.

Propchange: db/derby/code/trunk/tools/release/notices/simpleJson.txt
------------------------------------------------------------------------------
    svn:eol-style = native