]> granicus.if.org Git - postgresql/commitdiff
JDBC checkin fixing the following bugs:
authorBarry Lind <barry@xythos.com>
Mon, 2 Sep 2002 03:07:36 +0000 (03:07 +0000)
committerBarry Lind <barry@xythos.com>
Mon, 2 Sep 2002 03:07:36 +0000 (03:07 +0000)
  Fixed support in the driver for notifications (added PGConnection.getNotifications()) - problem reported by Benjamin.Feinstein@guardent.com
  Worked around server problems with int8/int2 and constants; quote values when they are intended to bind to an int8/int2 column - reported by many
  Fixed bug in the Array interface with string parsing not handling escaped characters correctly - reported by devajx@yahoo.com
  Added workaround to support 'infinity' and '-infinity' for dates - reported bydmitry@openratings.com
  Fixed some performance issues with setBlob - reported by d.wall@computer.org
  Added support for using new prepared statements functionality in 7.3 (added PGStatement.setUseServerPrepare() and isUseServerPrepare() methods)

 Modified Files:
  jdbc/org/postgresql/PGConnection.java
  jdbc/org/postgresql/PGStatement.java
  jdbc/org/postgresql/core/QueryExecutor.java
  jdbc/org/postgresql/jdbc1/AbstractJdbc1Connection.java
  jdbc/org/postgresql/jdbc1/AbstractJdbc1ResultSet.java
  jdbc/org/postgresql/jdbc1/AbstractJdbc1Statement.java
  jdbc/org/postgresql/jdbc2/AbstractJdbc2Statement.java
  jdbc/org/postgresql/jdbc2/Array.java
 Added Files:
  jdbc/org/postgresql/PGNotification.java
  jdbc/org/postgresql/core/Notification.java

src/interfaces/jdbc/org/postgresql/PGConnection.java
src/interfaces/jdbc/org/postgresql/PGNotification.java [new file with mode: 0644]
src/interfaces/jdbc/org/postgresql/PGStatement.java
src/interfaces/jdbc/org/postgresql/core/Notification.java [new file with mode: 0644]
src/interfaces/jdbc/org/postgresql/core/QueryExecutor.java
src/interfaces/jdbc/org/postgresql/jdbc1/AbstractJdbc1Connection.java
src/interfaces/jdbc/org/postgresql/jdbc1/AbstractJdbc1ResultSet.java
src/interfaces/jdbc/org/postgresql/jdbc1/AbstractJdbc1Statement.java
src/interfaces/jdbc/org/postgresql/jdbc2/AbstractJdbc2Statement.java
src/interfaces/jdbc/org/postgresql/jdbc2/Array.java

index c05f31222c57a046b3a678687d7f263913c4a200..2d22a318b0a4dd4e767f1ec329ab91844cf7aa42 100644 (file)
@@ -7,7 +7,7 @@ import org.postgresql.core.Encoding;
 import org.postgresql.fastpath.Fastpath;
 import org.postgresql.largeobject.LargeObjectManager;
 
-/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/Attic/PGConnection.java,v 1.1 2002/07/23 03:59:55 barry Exp $
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/Attic/PGConnection.java,v 1.2 2002/09/02 03:07:36 barry Exp $
  * This interface defines PostgreSQL extentions to the java.sql.Connection interface.
  * Any java.sql.Connection object returned by the driver will also implement this 
  * interface
@@ -68,5 +68,14 @@ public interface PGConnection
      */
     public Object getObject(String type, String value) throws SQLException;
 
+
+    /*
+     * This method returns any notifications that have been received 
+     * since the last call to this method.
+     * Returns null if there have been no notifications.
+     */
+    public PGNotification[] getNotifications();
+
+
 }
 
diff --git a/src/interfaces/jdbc/org/postgresql/PGNotification.java b/src/interfaces/jdbc/org/postgresql/PGNotification.java
new file mode 100644 (file)
index 0000000..0413e9b
--- /dev/null
@@ -0,0 +1,20 @@
+package org.postgresql;
+
+
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/Attic/PGNotification.java,v 1.1 2002/09/02 03:07:36 barry Exp $
+ * This interface defines PostgreSQL extention for Notifications
+ */
+public interface PGNotification
+{
+    /* 
+     * Returns name of this notification
+     */
+    public String getName();
+
+    /*
+     * Returns the process id of the backend process making this notification
+     */
+    public int getPID();
+
+}
+
index 1295afbe5aa57e6a571c2dae2b22fac954df5b7f..a226246a81d197d141275a71d1d222ad6f8aa894 100644 (file)
@@ -3,7 +3,7 @@ package org.postgresql;
 
 import java.sql.*;
 
-/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/Attic/PGStatement.java,v 1.3 2002/07/23 03:59:55 barry Exp $
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/Attic/PGStatement.java,v 1.4 2002/09/02 03:07:36 barry Exp $
  * This interface defines PostgreSQL extentions to the java.sql.Statement interface.
  * Any java.sql.Statement object returned by the driver will also implement this 
  * interface
@@ -18,4 +18,8 @@ public interface PGStatement
         */
         public long getLastOID() throws SQLException;
 
+        public void setUseServerPrepare(boolean flag);
+
+        public boolean isUseServerPrepare();
+
 }
diff --git a/src/interfaces/jdbc/org/postgresql/core/Notification.java b/src/interfaces/jdbc/org/postgresql/core/Notification.java
new file mode 100644 (file)
index 0000000..9612df4
--- /dev/null
@@ -0,0 +1,32 @@
+package org.postgresql.core;
+
+
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/core/Attic/Notification.java,v 1.1 2002/09/02 03:07:36 barry Exp $
+ * This is the implementation of the PGNotification interface
+ */
+public class Notification implements org.postgresql.PGNotification
+{
+    public Notification(String p_name, int p_pid) {
+       m_name = p_name;
+        m_pid = p_pid;
+    }
+
+    /* 
+     * Returns name of this notification
+     */
+    public String getName() {
+        return m_name;
+    }
+
+    /*
+     * Returns the process id of the backend process making this notification
+     */
+    public int getPID() {
+       return m_pid;
+    }
+
+    private String m_name;
+    private int m_pid;
+
+}
+
index 66b2c9341b2be95898c56db4f51d14bdb2cf2c2f..0a842c193cf2ec19a682061a2f47ce7deea2f920 100644 (file)
@@ -13,7 +13,7 @@ import org.postgresql.util.PSQLException;
  * <p>The lifetime of a QueryExecutor object is from sending the query
  * until the response has been received from the backend.
  *
- * $Id: QueryExecutor.java,v 1.14 2002/08/23 20:45:49 barry Exp $
+ * $Id: QueryExecutor.java,v 1.15 2002/09/02 03:07:36 barry Exp $
  */
 
 public class QueryExecutor
@@ -75,6 +75,7 @@ public class QueryExecutor
                                         case 'A':      // Asynchronous Notify
                                                 int pid = pg_stream.ReceiveInteger(4);
                                                 String msg = pg_stream.ReceiveString(connection.getEncoding());
+                                               connection.addNotification(new org.postgresql.core.Notification(msg, pid));
                                                 break;
                                         case 'B':      // Binary Data Transfer
                                                 receiveTuple(true);
index 566098d04cca521b6153ad3d04aaddf4a3f7d1e1..4721acc4353f7210510bdbad1ade2e82ebd1f988 100644 (file)
@@ -6,6 +6,7 @@ import java.net.ConnectException;
 import java.sql.*;
 import java.util.*;
 import org.postgresql.Driver;
+import org.postgresql.PGNotification;
 import org.postgresql.PG_Stream;
 import org.postgresql.core.*;
 import org.postgresql.fastpath.Fastpath;
@@ -13,7 +14,7 @@ import org.postgresql.largeobject.LargeObjectManager;
 import org.postgresql.util.*;
 
 
-/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc1/Attic/AbstractJdbc1Connection.java,v 1.6 2002/09/01 23:56:13 davec Exp $
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc1/Attic/AbstractJdbc1Connection.java,v 1.7 2002/09/02 03:07:36 barry Exp $
  * This class defines methods of the jdbc1 specification.  This class is
  * extended by org.postgresql.jdbc2.AbstractJdbc2Connection which adds the jdbc2
  * methods.  The real Connection class (for jdbc1) is org.postgresql.jdbc1.Jdbc1Connection
@@ -34,6 +35,8 @@ public abstract class AbstractJdbc1Connection implements org.postgresql.PGConnec
         protected int pid;
         protected int ckey;
 
+        private Vector m_notifications;
+
         /*
          The encoding to use for this connection.
          */
@@ -1309,7 +1312,22 @@ public abstract class AbstractJdbc1Connection implements org.postgresql.PGConnec
                                                                                                Types.TIMESTAMP, Types.TIMESTAMP, Types.TIMESTAMP
                                                                                        };
 
-
+    //Methods to support postgres notifications
+    public void addNotification(org.postgresql.PGNotification p_notification) {
+       if (m_notifications == null) 
+           m_notifications = new Vector();
+        m_notifications.addElement(p_notification);
+    }
+
+    public PGNotification[] getNotifications() {
+        PGNotification[] l_return = null;
+       if (m_notifications != null) {
+            l_return = new PGNotification[m_notifications.size()];
+            m_notifications.copyInto(l_return);
+       }
+        m_notifications = null;
+       return l_return;
+    }
 }
 
 
index ddec830c4c62f96a5b433899d2ba404db2515561..0a7e0eb0fece1861a526bfe23190e9b7d85c8c50 100644 (file)
@@ -13,7 +13,7 @@ import org.postgresql.largeobject.*;
 import org.postgresql.util.PGbytea;
 import org.postgresql.util.PSQLException;
 
-/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc1/Attic/AbstractJdbc1ResultSet.java,v 1.4 2002/08/16 17:51:38 barry Exp $
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc1/Attic/AbstractJdbc1ResultSet.java,v 1.5 2002/09/02 03:07:36 barry Exp $
  * This class defines methods of the jdbc1 specification.  This class is
  * extended by org.postgresql.jdbc2.AbstractJdbc2ResultSet which adds the jdbc2
  * methods.  The real ResultSet class (for jdbc1) is org.postgresql.jdbc1.Jdbc1ResultSet
@@ -934,6 +934,15 @@ public abstract class AbstractJdbc1ResultSet
                        }
                        else
                        {
+                                if (slen == 8 && s.equals("infinity"))
+                                    //java doesn't have a concept of postgres's infinity
+                                    //so set to an arbitrary future date
+                                    s = "9999-01-01";
+                               if (slen == 9 && s.equals("-infinity"))
+                                    //java doesn't have a concept of postgres's infinity
+                                    //so set to an arbitrary old date
+                                    s = "0001-01-01";
+
                                // We must just have a date. This case is
                                // needed if this method is called on a date
                                // column
index 5f410f999517f2b7855ddd676ec394d3e0bad27c..600cb42f56a4d5eb2ab1c5592b44e908d340feb2 100644 (file)
@@ -8,7 +8,7 @@ import java.util.Vector;
 import org.postgresql.largeobject.*;
 import org.postgresql.util.*;
 
-/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc1/Attic/AbstractJdbc1Statement.java,v 1.5 2002/08/23 20:45:49 barry Exp $
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc1/Attic/AbstractJdbc1Statement.java,v 1.6 2002/09/02 03:07:36 barry Exp $
  * This class defines methods of the jdbc1 specification.  This class is
  * extended by org.postgresql.jdbc2.AbstractJdbc2Statement which adds the jdbc2
  * methods.  The real Statement class (for jdbc1) is org.postgresql.jdbc1.Jdbc1Statement
@@ -44,7 +44,13 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
 
         //Used by the preparedstatement style methods
        protected String[] m_sqlFragments;
+       private String[] m_origSqlFragments;
+       private String[] m_executeSqlFragments;
        protected Object[] m_binds = new Object[0];
+        private String[] m_bindTypes = new String[0];
+        private String m_statementName = null;
+        private boolean m_useServerPrepare = false;
+        private static int m_preparedCount = 1;
 
        //Used by the callablestatement style methods
        private static final String JDBC_SYNTAX = "{[? =] call <some_function> ([? [,?]*]) }";
@@ -102,11 +108,13 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
 
                m_sqlFragments = new String[v.size()];
                m_binds = new String[v.size() - 1];
+                m_bindTypes = new String[v.size() - 1];
  //BJL why if binds is new???
                clearParameters();
 
                for (i = 0 ; i < m_sqlFragments.length; ++i)
                        m_sqlFragments[i] = (String)v.elementAt(i);
+
        }
 
 
@@ -207,6 +215,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                        throw new PSQLException("postgresql.call.noreturntype");
                if (isFunction) { // set entry 1 to dummy entry..
                        m_binds[0] = ""; // dummy entry which ensured that no one overrode
+                       m_bindTypes[0] = PG_TEXT; 
                        // and calls to setXXX (2,..) really went to first arg in a function call..
                }
 
@@ -220,6 +229,53 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                                rs.close();
                }
 
+                //Use server prepared statements if directed
+                if (m_useServerPrepare) {
+                   if (m_statementName == null) {
+                       m_statementName = "JDBC_STATEMENT_" + m_preparedCount++;
+                        m_origSqlFragments = new String[m_sqlFragments.length];
+                        m_executeSqlFragments = new String[m_sqlFragments.length];
+                        System.arraycopy(m_sqlFragments, 0, m_origSqlFragments, 0, m_sqlFragments.length);
+                        m_executeSqlFragments[0] = "EXECUTE " + m_statementName;
+                        if (m_sqlFragments.length > 1) {
+                            m_executeSqlFragments[0] = m_executeSqlFragments[0] + "(";
+                           for(int i = 1; i < m_bindTypes.length; i++) {
+                               m_executeSqlFragments[i] = ", ";
+                            }
+                           m_executeSqlFragments[m_bindTypes.length] = ")";
+                        }
+                       synchronized (sbuf) {
+                           sbuf.setLength(0);
+                            sbuf.append("PREPARE ");
+                            sbuf.append(m_statementName);
+                            if (m_origSqlFragments.length > 1) {
+                                sbuf.append("(");
+                               for(int i = 0; i < m_bindTypes.length - 1; i++) {
+                                    sbuf.append(m_bindTypes[i]);
+                                    sbuf.append(", ");
+                                }
+                               sbuf.append(m_bindTypes[m_bindTypes.length - 1]);
+                                sbuf.append(")");
+                            }
+                            sbuf.append(" AS ");
+                           sbuf.append(m_origSqlFragments[0]);
+                           for(int i = 1; i < m_origSqlFragments.length; i++) {
+                                sbuf.append(" $");
+                                sbuf.append(i);
+                                sbuf.append(" ");
+                                sbuf.append(m_origSqlFragments[i]);
+                            }
+                            sbuf.append("; ");
+                           
+                            sbuf.append(m_executeSqlFragments[0]);
+                            m_sqlFragments[0] = sbuf.toString();
+                            System.arraycopy(m_executeSqlFragments, 1, m_sqlFragments, 1, m_sqlFragments.length - 1);
+                       }
+
+                   } else {
+                        m_sqlFragments = m_executeSqlFragments;
+                   }
+               }
 
                // New in 7.1, pass Statement so that ExecSQL can customise to it
                result = ((AbstractJdbc1Connection)connection).ExecSQL(m_sqlFragments, m_binds, (java.sql.Statement)this);
@@ -618,7 +674,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setNull(int parameterIndex, int sqlType) throws SQLException
        {
-               set(parameterIndex, "null");
+               bind(parameterIndex, "null", PG_TEXT);
        }
 
        /*
@@ -631,7 +687,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setBoolean(int parameterIndex, boolean x) throws SQLException
        {
-               set(parameterIndex, x ? "'t'" : "'f'");
+               bind(parameterIndex, x ? "'t'" : "'f'", PG_BOOLEAN);
        }
 
        /*
@@ -644,7 +700,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setByte(int parameterIndex, byte x) throws SQLException
        {
-               set(parameterIndex, Integer.toString(x));
+               bind(parameterIndex, Integer.toString(x), PG_TEXT);
        }
 
        /*
@@ -657,7 +713,10 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setShort(int parameterIndex, short x) throws SQLException
        {
-               set(parameterIndex, Integer.toString(x));
+               //Note this should be fixed
+                //as soon as the backend correctly supports int8 type
+                //comparisons
+               bind(parameterIndex,"'" + Integer.toString(x) +"'", PG_INT2);
        }
 
        /*
@@ -670,7 +729,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setInt(int parameterIndex, int x) throws SQLException
        {
-               set(parameterIndex, Integer.toString(x));
+               bind(parameterIndex, Integer.toString(x), PG_INTEGER);
        }
 
        /*
@@ -683,7 +742,10 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setLong(int parameterIndex, long x) throws SQLException
        {
-               set(parameterIndex, Long.toString(x));
+               //Note this should be fixed
+                //as soon as the backend correctly supports int8 type
+                //comparisons
+               bind(parameterIndex, "'"+Long.toString(x)+"'", PG_INT8);
        }
 
        /*
@@ -696,7 +758,10 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setFloat(int parameterIndex, float x) throws SQLException
        {
-               set(parameterIndex, Float.toString(x));
+               //Note this should be fixed
+                //as soon as the backend correctly supports int8 type
+                //comparisons
+               bind(parameterIndex, "'"+Float.toString(x)+"'", PG_FLOAT);
        }
 
        /*
@@ -709,7 +774,10 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         */
        public void setDouble(int parameterIndex, double x) throws SQLException
        {
-               set(parameterIndex, Double.toString(x));
+               //Note this should be fixed
+                //as soon as the backend correctly supports int8 type
+                //comparisons
+               bind(parameterIndex, "'"+Double.toString(x)+"'", PG_DOUBLE);
        }
 
        /*
@@ -727,7 +795,10 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                        setNull(parameterIndex, Types.OTHER);
                else
                {
-                   set(parameterIndex, x.toString());
+                   //Note this should be fixed
+                    //as soon as the backend correctly supports int8 type
+                    //comparisons
+                   bind(parameterIndex, "'"+x.toString()+"'", PG_NUMERIC);
                }
        }
 
@@ -742,6 +813,11 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         * @exception SQLException if a database access error occurs
         */
        public void setString(int parameterIndex, String x) throws SQLException
+       {
+           setString(parameterIndex, x, PG_TEXT);
+       }
+
+       public void setString(int parameterIndex, String x, String type) throws SQLException
        {
                // if the passed string is null, then set this column to null
                if (x == null)
@@ -765,7 +841,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                                        sbuf.append(c);
                                }
                                sbuf.append('\'');
-                               set(parameterIndex, sbuf.toString());
+                               bind(parameterIndex, sbuf.toString(), type);
                        }
                }
        }
@@ -795,7 +871,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                        }
                        else
                        {
-                               setString(parameterIndex, PGbytea.toPGString(x));
+                               setString(parameterIndex, PGbytea.toPGString(x), PG_TEXT);
                        }
                }
                else
@@ -826,7 +902,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                }
                else
                {
-                       set(parameterIndex, "'" + x.toString() + "'");
+                       bind(parameterIndex, "'" + x.toString() + "'", PG_DATE);
                }
        }
 
@@ -846,7 +922,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                }
                else
                {
-                       set(parameterIndex, "'" + x.toString() + "'");
+                       bind(parameterIndex, "'" + x.toString() + "'", PG_TIME);
                }
        }
 
@@ -932,7 +1008,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                                   sbuf.append(l_minos);
                                 }
                                sbuf.append("'");
-                               set(parameterIndex, sbuf.toString());
+                               bind(parameterIndex, sbuf.toString(), PG_TIMESTAMPTZ);
                        }
 
                }
@@ -969,7 +1045,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                                InputStreamReader l_inStream = new InputStreamReader(x, "ASCII");
                                char[] l_chars = new char[length];
                                int l_charsRead = l_inStream.read(l_chars, 0, length);
-                               setString(parameterIndex, new String(l_chars, 0, l_charsRead));
+                               setString(parameterIndex, new String(l_chars, 0, l_charsRead), PG_TEXT);
                        }
                        catch (UnsupportedEncodingException l_uee)
                        {
@@ -1018,7 +1094,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                                InputStreamReader l_inStream = new InputStreamReader(x, "UTF-8");
                                char[] l_chars = new char[length];
                                int l_charsRead = l_inStream.read(l_chars, 0, length);
-                               setString(parameterIndex, new String(l_chars, 0, l_charsRead));
+                               setString(parameterIndex, new String(l_chars, 0, l_charsRead), PG_TEXT);
                        }
                        catch (UnsupportedEncodingException l_uee)
                        {
@@ -1130,8 +1206,10 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
        {
                int i;
 
-               for (i = 0 ; i < m_binds.length ; i++)
+               for (i = 0 ; i < m_binds.length ; i++) {
                        m_binds[i] = null;
+                        m_bindTypes[i] = null;
+               }
        }
 
        /*
@@ -1162,9 +1240,11 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                }
                switch (targetSqlType)
                {
+                       case Types.INTEGER:
+                                       bind(parameterIndex, x.toString(), PG_INTEGER);
+                               break;
                        case Types.TINYINT:
                        case Types.SMALLINT:
-                       case Types.INTEGER:
                        case Types.BIGINT:
                        case Types.REAL:
                        case Types.FLOAT:
@@ -1172,9 +1252,12 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                        case Types.DECIMAL:
                        case Types.NUMERIC:
                                if (x instanceof Boolean)
-                                       set(parameterIndex, ((Boolean)x).booleanValue() ? "1" : "0");
+                                       bind(parameterIndex, ((Boolean)x).booleanValue() ? "1" : "0", PG_BOOLEAN);
                                else
-                                       set(parameterIndex, x.toString());
+                                       //Note this should be fixed
+                                       //as soon as the backend correctly supports int8 type
+                                       //comparisons
+                                       bind(parameterIndex, "'"+x.toString()+"'", PG_NUMERIC);
                                break;
                        case Types.CHAR:
                        case Types.VARCHAR:
@@ -1193,7 +1276,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                        case Types.BIT:
                                if (x instanceof Boolean)
                                {
-                                       set(parameterIndex, ((Boolean)x).booleanValue() ? "TRUE" : "FALSE");
+                                       bind(parameterIndex, ((Boolean)x).booleanValue() ? "TRUE" : "FALSE", PG_TEXT);
                                }
                                else
                                {
@@ -1205,7 +1288,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                                setObject(parameterIndex, x);
                                break;
                        case Types.OTHER:
-                               setString(parameterIndex, ((PGobject)x).getValue());
+                               setString(parameterIndex, ((PGobject)x).getValue(), PG_TEXT);
                                break;
                        default:
                                throw new PSQLException("postgresql.prep.type");
@@ -1255,7 +1338,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                else if (x instanceof Boolean)
                        setBoolean(parameterIndex, ((Boolean)x).booleanValue());
                else if (x instanceof PGobject)
-                       setString(parameterIndex, ((PGobject)x).getValue());
+                       setString(parameterIndex, ((PGobject)x).getValue(), PG_TEXT);
                else
                        // Try to store java object in database
                        setSerialize(parameterIndex, connection.storeObject(x), x.getClass().getName() );
@@ -1579,13 +1662,14 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
         * @param s a string to be stored
         * @exception SQLException if something goes wrong
         */
-       protected void set(int paramIndex, String s) throws SQLException
+       protected void bind(int paramIndex, Object s, String type) throws SQLException
        {
                if (paramIndex < 1 || paramIndex > m_binds.length)
                        throw new PSQLException("postgresql.prep.range");
                if (paramIndex == 1 && isFunction) // need to registerOut instead
                        throw new PSQLException ("postgresql.call.funcover");             
                m_binds[paramIndex - 1] = s;
+                m_bindTypes[paramIndex - 1] = type;
        }
 
        /*
@@ -1607,7 +1691,7 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
                // This cannot be just a plain OID because then there would be ambiguity
                // between when you want the oid itself and when you want the object
                // an oid references.
-               set(parameterIndex, Long.toString(x) + "::" + tablename );
+               bind(parameterIndex, Long.toString(x) + "::" + tablename, PG_TEXT );
        }
 
        /** 
@@ -1675,4 +1759,27 @@ public abstract class AbstractJdbc1Statement implements org.postgresql.PGStateme
        }
                
 
+
+    public void setUseServerPrepare(boolean flag) {
+       m_useServerPrepare = flag;
+    }
+
+    public boolean isUseServerPrepare() {
+       return m_useServerPrepare;
+    }
+
+
+    private static final String PG_TEXT = "text";
+    private static final String PG_INTEGER = "integer";
+    private static final String PG_INT2 = "int2";
+    private static final String PG_INT8 = "int8";
+    private static final String PG_NUMERIC = "numeric";
+    private static final String PG_FLOAT = "float";
+    private static final String PG_DOUBLE = "double";
+    private static final String PG_BOOLEAN = "boolean";
+    private static final String PG_DATE = "date";
+    private static final String PG_TIME = "time";
+    private static final String PG_TIMESTAMPTZ = "timestamptz";
+
+
 }
index 457f36e9413ba4728d0daa828b2188b254eb7711..3dd4e748bcf31eee0fea9381aabbdc4f16064076 100644 (file)
@@ -8,7 +8,7 @@ import java.util.Vector;
 import org.postgresql.largeobject.*;
 import org.postgresql.util.PSQLException;
 
-/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc2/Attic/AbstractJdbc2Statement.java,v 1.4 2002/08/23 20:45:49 barry Exp $
+/* $Header: /cvsroot/pgsql/src/interfaces/jdbc/org/postgresql/jdbc2/Attic/AbstractJdbc2Statement.java,v 1.5 2002/09/02 03:07:36 barry Exp $
  * This class defines methods of the jdbc2 specification.  This class extends
  * org.postgresql.jdbc1.AbstractJdbc1Statement which provides the jdbc1
  * methods.  The real Statement class (for jdbc2) is org.postgresql.jdbc2.Jdbc2Statement
@@ -172,23 +172,23 @@ public abstract class AbstractJdbc2Statement extends org.postgresql.jdbc1.Abstra
        public void setBlob(int i, Blob x) throws SQLException
        {
                InputStream l_inStream = x.getBinaryStream();
-               int l_length = (int) x.length();
                LargeObjectManager lom = connection.getLargeObjectAPI();
                int oid = lom.create();
                LargeObject lob = lom.open(oid);
                OutputStream los = lob.getOutputStream();
+               byte[] buf = new byte[4096];
                try
                {
                        // could be buffered, but then the OutputStream returned by LargeObject
                        // is buffered internally anyhow, so there would be no performance
                        // boost gained, if anything it would be worse!
-                       int c = l_inStream.read();
-                       int p = 0;
-                       while (c > -1 && p < l_length)
+                       int bytesRemaining = (int)x.length();
+                       int numRead = l_inStream.read(buf,0,Math.min(buf.length,bytesRemaining));
+                       while (numRead != -1 && bytesRemaining > 0)
                        {
-                               los.write(c);
-                               c = l_inStream.read();
-                               p++;
+                               bytesRemaining -= numRead;
+                               los.write(buf,0,numRead);
+                               numRead = l_inStream.read(buf,0,Math.min(buf.length,bytesRemaining));
                        }
                        los.close();
                }
index 6be102691bc2b3cf028fb36e829e5c66ac462bd1..94cc5aab598efac4eaa385a96fc00767c55bd09e 100644 (file)
@@ -88,6 +88,9 @@ public class Array implements java.sql.Array
                        boolean insideString = false;
                        for ( int i = 0; i < chars.length; i++ )
                        {
+                               if ( chars[i] == '\\' )
+                                       //escape character that we need to skip
+                                       i++;
                                if ( chars[i] == '{' )
                                {
                                        if ( foundOpen )  // Only supports 1-D arrays for now