diff -ruN postgresql-jdbc-8.4-701.src/build.properties postgresql-jdbc-8.4-701.src_without_CopyManager/build.properties --- postgresql-jdbc-8.4-701.src/build.properties 2009-07-01 07:15:53.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/build.properties 2008-01-31 11:25:52.000000000 +0100 @@ -1,10 +1,10 @@ # Default build parameters. These may be overridden by local configuration # settings in build.local.properties. # -# $PostgreSQL: pgjdbc/build.properties,v 1.13 2009/07/01 05:15:53 jurka Exp $ +# $PostgreSQL: pgjdbc/build.properties,v 1.12 2008/01/31 10:25:52 jurka Exp $ major=8 minor=4 -fullversion=8.4 +fullversion=8.4devel def_pgport=5432 enable_debug=yes diff -ruN postgresql-jdbc-8.4-701.src/build.xml postgresql-jdbc-8.4-701.src_without_CopyManager/build.xml --- postgresql-jdbc-8.4-701.src/build.xml 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/build.xml 2008-10-08 20:25:33.000000000 +0200 @@ -8,7 +8,7 @@ This file now requires Ant 1.4.1. 2002-04-18 - $PostgreSQL: pgjdbc/build.xml,v 1.87 2009/07/01 05:00:39 jurka Exp $ + $PostgreSQL: pgjdbc/build.xml,v 1.84 2008/10/08 18:25:33 jurka Exp $ --> @@ -121,7 +121,6 @@ - @@ -167,9 +166,6 @@ - - - @@ -400,15 +396,11 @@ - - - - diff -ruN postgresql-jdbc-8.4-701.src/doc/pgjdbc.xml postgresql-jdbc-8.4-701.src_without_CopyManager/doc/pgjdbc.xml --- postgresql-jdbc-8.4-701.src/doc/pgjdbc.xml 2009-06-20 17:19:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/doc/pgjdbc.xml 2008-09-30 05:42:48.000000000 +0200 @@ -1,7 +1,7 @@ @@ -592,19 +592,6 @@ - socketTimeout = int - - - The timeout value used for socket read operations. If reading - from the server takes longer than this value, the connection is - closed. This can be used as both a brute force global query - timeout and a method of detecting network problems. The timeout - is specified in seconds and a value of zero means that it is disabled. - - - - - tcpKeepAlive = boolean @@ -615,23 +602,6 @@ - unknownLength = int - - - Certain postgresql types such as text do not - have a well defined length. When returning meta-data about - these types through functions like - ResultSetMetaData.getColumnDisplaySize - and ResultSetMetaData.getPrecision - we must provide a value and various client tools have - different ideas about what they would like to see. This - parameter specifies the length to return for types of - unknown length. - - - - - stringtype = String @@ -648,28 +618,6 @@ - - kerberosServerName = String - - - The Kerberos service name to use when authenticating with GSSAPI. This is - equivalent to libpq's PGKRBSRVNAME environment variable and defaults to - "postgres". - - - - - - jaasApplicationName = String - - - Specifies the name of the JAAS system or application - login configuration. - - - - - @@ -1270,7 +1218,7 @@ // Procedure call. CallableStatement proc = conn.prepareCall("{ ? = call refcursorfunc() }"); -proc.registerOutParameter(1, Types.OTHER); +proc.registerOutParameter(1, Types.Other); proc.execute(); ResultSet results = (ResultSet) proc.getObject(1); while (results.next()) { @@ -1295,7 +1243,7 @@ conn.setAutoCommit(false); CallableStatement proc = conn.prepareCall("{ ? = call refcursorfunc() }"); -proc.registerOutParameter(1, Types.OTHER); +proc.registerOutParameter(1, Types.Other); proc.execute(); String cursorName = proc.getString(1); proc.close(); diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/PGConnection.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/PGConnection.java --- postgresql-jdbc-8.4-701.src/org/postgresql/PGConnection.java 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/PGConnection.java 2008-04-15 06:23:52.000000000 +0200 @@ -3,14 +3,13 @@ * Copyright (c) 2003-2008, PostgreSQL Global Development Group * * IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/PGConnection.java,v 1.17 2009/07/01 05:00:39 jurka Exp $ +* $PostgreSQL: pgjdbc/org/postgresql/PGConnection.java,v 1.16 2008/04/15 04:23:52 jurka Exp $ * *------------------------------------------------------------------------- */ package org.postgresql; import java.sql.*; -import org.postgresql.copy.CopyManager; import org.postgresql.fastpath.Fastpath; import org.postgresql.largeobject.LargeObjectManager; @@ -30,12 +29,6 @@ public PGNotification[] getNotifications() throws SQLException; /** - * This returns the COPY API for the current connection. - * @since 8.4 - */ - public CopyManager getCopyAPI() throws SQLException; - - /** * This returns the LargeObject API for the current connection. * @since 7.3 */ diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyIn.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyIn.java --- postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyIn.java 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyIn.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,43 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/copy/CopyIn.java,v 1.1 2009/07/01 05:00:39 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.copy; - -import java.sql.SQLException; - -/** - * Copy bulk data from client into a PostgreSQL table very fast. - */ -public interface CopyIn extends CopyOperation { - - /** - * Writes specified part of given byte array to an open and writable copy operation. - * @param buf array of bytes to write - * @param off offset of first byte to write (normally zero) - * @param siz number of bytes to write (normally buf.length) - * @throws SQLException if the operation fails - */ - void writeToCopy(byte[] buf, int off, int siz) throws SQLException; - - /** - * Force any buffered output to be sent over the network to the - * backend. In general this is a useless operation as it will get - * pushed over in due time or when endCopy is called. Some specific - * modified server versions (Truviso) want this data sooner. - * If you are unsure if you need to use this method, don't. - */ - void flushCopy() throws SQLException; - - /** - * Finishes copy operation succesfully. - * @return number of updated rows for server 8.2 or newer (see getHandledRowCount()) - * @throws SQLException if the operation fails. - */ - public long endCopy() throws SQLException; -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyManager.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyManager.java --- postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyManager.java 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyManager.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,187 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/copy/CopyManager.java,v 1.1 2009/07/01 05:00:39 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ - -/** - * Bulk data copy for PostgreSQL - */ -package org.postgresql.copy; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.InputStream; -import java.io.Reader; -import java.io.Writer; -import java.sql.SQLException; - -import org.postgresql.core.Encoding; -import org.postgresql.core.QueryExecutor; -import org.postgresql.core.BaseConnection; -import org.postgresql.util.GT; -import org.postgresql.util.PSQLException; -import org.postgresql.util.PSQLState; - -/** - * API for PostgreSQL COPY bulk data transfer - */ -public class CopyManager { - // I don't know what the best buffer size is, so we let people specify it if - // they want, and if they don't know, we don't make them guess, so that if we - // do figure it out we can just set it here and they reap the rewards. - // Note that this is currently being used for both a number of bytes and a number - // of characters. - final static int DEFAULT_BUFFER_SIZE = 65536; - - private final Encoding encoding; - private final QueryExecutor queryExecutor; - - public CopyManager(BaseConnection connection) throws SQLException { - this.encoding = connection.getEncoding(); - this.queryExecutor = connection.getQueryExecutor(); - } - - public CopyIn copyIn(String sql) throws SQLException { - CopyOperation op = null; - try { - op = queryExecutor.startCopy(sql); - return (CopyIn) op; - } catch(ClassCastException cce) { - op.cancelCopy(); - throw new PSQLException(GT.tr("Requested CopyIn but got {0}", op.getClass().getName()), PSQLState.WRONG_OBJECT_TYPE, cce); - } - } - - public CopyOut copyOut(String sql) throws SQLException { - CopyOperation op = null; - try { - op = queryExecutor.startCopy(sql); - return (CopyOut) op; - } catch(ClassCastException cce) { - op.cancelCopy(); - throw new PSQLException(GT.tr("Requested CopyOut but got {0}", op.getClass().getName()), PSQLState.WRONG_OBJECT_TYPE, cce); - } - } - - /** - * Pass results of a COPY TO STDOUT query from database into a Writer. - * @param sql COPY TO STDOUT statement - * @param to the stream to write the results to (row by row) - * @return number of rows updated for server 8.2 or newer; -1 for older - * @throws SQLException on database usage errors - * @throws IOException upon writer or database connection failure - */ - public long copyOut(final String sql, Writer to) throws SQLException, IOException { - byte[] buf; - CopyOut cp = copyOut(sql); - try { - while ( (buf = cp.readFromCopy()) != null ) { - to.write(encoding.decode(buf)); - } - return cp.getHandledRowCount(); - } finally { // see to it that we do not leave the connection locked - if(cp.isActive()) - cp.cancelCopy(); - } - } - - /** - * Pass results of a COPY TO STDOUT query from database into an OutputStream. - * @param sql COPY TO STDOUT statement - * @param to the stream to write the results to (row by row) - * @return number of rows updated for server 8.2 or newer; -1 for older - * @throws SQLException on database usage errors - * @throws IOException upon output stream or database connection failure - */ - public long copyOut(final String sql, OutputStream to) throws SQLException, IOException { - byte[] buf; - CopyOut cp = copyOut(sql); - try { - while( (buf = cp.readFromCopy()) != null ) { - to.write(buf); - } - return cp.getHandledRowCount(); - } finally { // see to it that we do not leave the connection locked - if(cp.isActive()) - cp.cancelCopy(); - } - } - - /** - * Use COPY FROM STDIN for very fast copying from a Reader into a database table. - * @param sql COPY FROM STDIN statement - * @param from a CSV file or such - * @return number of rows updated for server 8.2 or newer; -1 for older - * @throws SQLException on database usage issues - * @throws IOException upon reader or database connection failure - */ - public long copyIn(final String sql, Reader from) throws SQLException, IOException { - return copyIn(sql, from, DEFAULT_BUFFER_SIZE); - } - - /** - * Use COPY FROM STDIN for very fast copying from a Reader into a database table. - * @param sql COPY FROM STDIN statement - * @param from a CSV file or such - * @param bufferSize number of characters to buffer and push over network to server at once - * @return number of rows updated for server 8.2 or newer; -1 for older - * @throws SQLException on database usage issues - * @throws IOException upon reader or database connection failure - */ - public long copyIn(final String sql, Reader from, int bufferSize) throws SQLException, IOException { - char[] cbuf = new char[bufferSize]; - int len; - CopyIn cp = copyIn(sql); - try { - while ( (len = from.read(cbuf)) > 0) { - byte[] buf = encoding.encode(new String(cbuf)); - cp.writeToCopy(buf, 0, buf.length); - } - return cp.endCopy(); - } finally { // see to it that we do not leave the connection locked - if(cp.isActive()) - cp.cancelCopy(); - } - } - - /** - * Use COPY FROM STDIN for very fast copying from an InputStream into a database table. - * @param sql COPY FROM STDIN statement - * @param from a CSV file or such - * @return number of rows updated for server 8.2 or newer; -1 for older - * @throws SQLException on database usage issues - * @throws IOException upon input stream or database connection failure - */ - public long copyIn(final String sql, InputStream from) throws SQLException, IOException { - return copyIn(sql, from, DEFAULT_BUFFER_SIZE); - } - - /** - * Use COPY FROM STDIN for very fast copying from an InputStream into a database table. - * @param sql COPY FROM STDIN statement - * @param from a CSV file or such - * @param bufferSize number of bytes to buffer and push over network to server at once - * @return number of rows updated for server 8.2 or newer; -1 for older - * @throws SQLException on database usage issues - * @throws IOException upon input stream or database connection failure - */ - public long copyIn(final String sql, InputStream from, int bufferSize) throws SQLException, IOException { - byte[] buf = new byte[bufferSize]; - int len; - CopyIn cp = copyIn(sql); - try { - while( (len = from.read(buf)) > 0 ) { - cp.writeToCopy(buf, 0, len); - } - return cp.endCopy(); - } finally { // see to it that we do not leave the connection locked - if(cp.isActive()) - cp.cancelCopy(); - } - } -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyOperation.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyOperation.java --- postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyOperation.java 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyOperation.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,55 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/copy/CopyOperation.java,v 1.1 2009/07/01 05:00:39 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.copy; - -import java.sql.SQLException; - -/** - * Exchange bulk data between client and PostgreSQL database tables. - * See CopyIn and CopyOut for full interfaces for corresponding copy directions. - */ -public interface CopyOperation { - - /** - * @return number of fields in each row for this operation - */ - int getFieldCount(); - - /** - * @return overall format of each row: 0 = textual, 1 = binary - */ - int getFormat(); - - /** - * @param field number of field (0..fieldCount()-1) - * @return format of requested field: 0 = textual, 1 = binary - */ - int getFieldFormat(int field); - - /** - * @return is connection reserved for this Copy operation? - */ - boolean isActive(); - - /** - * Cancels this copy operation, discarding any exchanged data. - * @throws SQLException if cancelling fails - */ - void cancelCopy() throws SQLException; - - /** - * After succesful end of copy, returns the number - * of database records handled in that operation. - * Only implemented in PostgreSQL server version 8.2 and up. - * Otherwise, returns -1. - * @return number of handled rows or -1 - */ - public long getHandledRowCount(); -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyOut.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyOut.java --- postgresql-jdbc-8.4-701.src/org/postgresql/copy/CopyOut.java 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/CopyOut.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,16 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/copy/CopyOut.java,v 1.1 2009/07/01 05:00:39 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.copy; - -import java.sql.SQLException; - -public interface CopyOut extends CopyOperation { - byte[] readFromCopy() throws SQLException; -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/copy/PGCopyInputStream.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/PGCopyInputStream.java --- postgresql-jdbc-8.4-701.src/org/postgresql/copy/PGCopyInputStream.java 2009-07-01 07:00:39.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/copy/PGCopyInputStream.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,153 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/copy/PGCopyInputStream.java,v 1.1 2009/07/01 05:00:39 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.copy; - -import java.io.IOException; -import java.io.InputStream; -import java.sql.SQLException; - -import org.postgresql.PGConnection; -import org.postgresql.util.GT; -import org.postgresql.util.PSQLException; -import org.postgresql.util.PSQLState; - -/** - * InputStream for reading from a PostgreSQL COPY TO STDOUT operation - */ -public class PGCopyInputStream extends InputStream implements CopyOut { - private CopyOut op; - private byte[] buf; - private int at, len; - - /** - * Uses given connection for specified COPY TO STDOUT operation - * @param connection database connection to use for copying (protocol version 3 required) - * @param sql COPY TO STDOUT statement - * @throws SQLException if initializing the operation fails - */ - public PGCopyInputStream(PGConnection connection, String sql) throws SQLException { - this(connection.getCopyAPI().copyOut(sql)); - } - - /** - * Use given CopyOut operation for reading - * @param op COPY TO STDOUT operation - * @throws SQLException if initializing the operation fails - */ - public PGCopyInputStream(CopyOut op) { - this.op = op; - } - - private boolean gotBuf() throws IOException { - if(at >= len) { - try { - buf = op.readFromCopy(); - } catch(SQLException sqle) { - throw new IOException(GT.tr("Copying from database failed: {0}", sqle)); - } - if(buf == null) { - at = -1; - return false; - } else { - at = 0; - len = buf.length; - return true; - } - } - return buf != null; - } - - private void checkClosed() throws IOException { - if (op == null) { - throw new IOException(GT.tr("This copy stream is closed.")); - } - } - - - public int available() throws IOException { - checkClosed(); - return ( buf != null ? len - at : 0 ); - } - - public int read() throws IOException { - checkClosed(); - return gotBuf() ? buf[at++] : -1; - } - - public int read(byte[] buf) throws IOException { - return read(buf, 0, buf.length); - } - - public int read(byte[] buf, int off, int siz) throws IOException { - checkClosed(); - int got = 0; - while( got < siz && gotBuf() ) { - buf[off+got++] = this.buf[at++]; - } - return got; - } - - public byte[] readFromCopy() throws SQLException { - byte[] result = buf; - try { - if(gotBuf()) { - if(at>0 || len < buf.length) { - byte[] ba = new byte[len-at]; - for(int i=at; i255) - throw new IOException(GT.tr("Cannot write to copy a byte of value {0}", new Integer(b))); - singleByteBuffer[0] = (byte)b; - write(singleByteBuffer, 0, 1); - } - - public void write(byte[] buf) throws IOException { - write(buf, 0, buf.length); - } - - public void write(byte[] buf, int off, int siz) throws IOException { - checkClosed(); - try { - writeToCopy(buf, off, siz); - } catch(SQLException se) { - IOException ioe = new IOException("Write to copy failed."); - ioe.initCause(se); - throw ioe; - } - } - - private void checkClosed() throws IOException { - if (op == null) { - throw new IOException(GT.tr("This copy stream is closed.")); - } - } - - public void close() throws IOException { - // Don't complain about a double close. - if (op == null) - return; - - try{ - endCopy(); - } catch(SQLException se) { - IOException ioe = new IOException("Ending write to copy failed."); - ioe.initCause(se); - throw ioe; - } - op = null; - } - - public void flush() throws IOException { - try { - op.writeToCopy(copyBuffer, 0, at); - at = 0; - op.flushCopy(); - } catch (SQLException e) { - IOException ioe = new IOException("Unable to flush stream"); - ioe.initCause(e); - throw ioe; - } - } - - public void writeToCopy(byte[] buf, int off, int siz) throws SQLException { - if(at > 0 && siz > copyBuffer.length - at) { // would not fit into rest of our buf, so flush buf - op.writeToCopy(copyBuffer, 0, at); - at = 0; - } - if(siz > copyBuffer.length) { // would still not fit into buf, so just pass it through - op.writeToCopy(buf, off, siz); - } else { // fits into our buf, so save it there - System.arraycopy(buf, off, copyBuffer, at, siz); - at += siz; - } - } - - public int getFormat() { - return op.getFormat(); - } - - public int getFieldFormat(int field) { - return op.getFieldFormat(field); - } - - public void cancelCopy() throws SQLException { - op.cancelCopy(); - } - - public int getFieldCount() { - return op.getFieldCount(); - } - - public boolean isActive() { - return op.isActive(); - } - - public void flushCopy() throws SQLException { - op.flushCopy(); - } - - public long endCopy() throws SQLException { - if(at > 0) { - op.writeToCopy(copyBuffer, 0, at); - } - op.endCopy(); - return getHandledRowCount(); - } - - public long getHandledRowCount() { - return op.getHandledRowCount(); - } - -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/core/QueryExecutor.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/QueryExecutor.java --- postgresql-jdbc-8.4-701.src/org/postgresql/core/QueryExecutor.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/QueryExecutor.java 2008-11-15 18:48:52.000000000 +0100 @@ -4,7 +4,7 @@ * Copyright (c) 2004, Open Cloud Limited. * * IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/core/QueryExecutor.java,v 1.44 2009/07/01 05:00:40 jurka Exp $ +* $PostgreSQL: pgjdbc/org/postgresql/core/QueryExecutor.java,v 1.43 2008/11/15 17:48:52 jurka Exp $ * *------------------------------------------------------------------------- */ @@ -12,8 +12,6 @@ import java.sql.SQLException; -import org.postgresql.copy.CopyOperation; - /** * Abstracts the protocol-specific details of executing a query. *

@@ -212,13 +210,4 @@ * @throws SQLException if an error occurs while executing the fastpath call */ byte[] fastpathCall(int fnid, ParameterList params, boolean suppressBegin) throws SQLException; - - /** - * Issues a COPY FROM STDIN / COPY TO STDOUT statement and returns - * handler for associated operation. Until the copy operation completes, - * no other database operation may be performed. - * Implemented for protocol version 3 only. - * @throws SQLException when initializing the given query fails - */ - CopyOperation startCopy(String sql) throws SQLException; } diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/core/v2/QueryExecutorImpl.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v2/QueryExecutorImpl.java --- postgresql-jdbc-8.4-701.src/org/postgresql/core/v2/QueryExecutorImpl.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v2/QueryExecutorImpl.java 2008-11-15 18:48:52.000000000 +0100 @@ -4,7 +4,7 @@ * Copyright (c) 2004, Open Cloud Limited. * * IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/core/v2/QueryExecutorImpl.java,v 1.22 2009/07/01 05:00:40 jurka Exp $ +* $PostgreSQL: pgjdbc/org/postgresql/core/v2/QueryExecutorImpl.java,v 1.21 2008/11/15 17:48:52 jurka Exp $ * *------------------------------------------------------------------------- */ @@ -19,7 +19,6 @@ import org.postgresql.util.PSQLException; import org.postgresql.util.PSQLState; import org.postgresql.util.GT; -import org.postgresql.copy.CopyOperation; /** * QueryExecutor implementation for the V2 protocol. @@ -606,8 +605,5 @@ private final ProtocolConnectionImpl protoConnection; private final PGStream pgStream; private final Logger logger; - - public CopyOperation startCopy(String sql) throws SQLException { - throw new PSQLException(GT.tr("Copy not implemented for protocol version 2"), PSQLState.NOT_IMPLEMENTED); - } } + diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/CopyInImpl.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/CopyInImpl.java --- postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/CopyInImpl.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/CopyInImpl.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,63 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/core/v3/CopyInImpl.java,v 1.1 2009/07/01 05:00:40 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.core.v3; - -import java.sql.SQLException; - -import org.postgresql.copy.CopyIn; - -/** - * Anticipated flow of a COPY FROM STDIN operation: - * - * CopyManager.copyIn() - * ->QueryExecutor.startCopy() - * - sends given query to server - * ->processCopyResults(): - * - receives CopyInResponse from Server - * - creates new CopyInImpl - * ->initCopy(): - * - receives copy metadata from server - * ->CopyInImpl.init() - * ->lock() connection for this operation - * - if query fails an exception is thrown - * - if query returns wrong CopyOperation, copyIn() cancels it before throwing exception - * <-return: new CopyInImpl holding lock on connection - * repeat CopyIn.writeToCopy() for all data - * ->CopyInImpl.writeToCopy() - * ->QueryExecutorImpl.writeToCopy() - * - sends given data - * ->processCopyResults() - * - parameterized not to block, just peek for new messages from server - * - on ErrorResponse, waits until protocol is restored and unlocks connection - * CopyIn.endCopy() - * ->CopyInImpl.endCopy() - * ->QueryExecutorImpl.endCopy() - * - sends CopyDone - * - processCopyResults() - * - on CommandComplete - * ->CopyOperationImpl.handleCommandComplete() - * - sets updatedRowCount when applicable - * - on ReadyForQuery unlock() connection for use by other operations - * <-return: CopyInImpl.getUpdatedRowCount() - */ -public class CopyInImpl extends CopyOperationImpl implements CopyIn { - - public void writeToCopy(byte[] data, int off, int siz) throws SQLException { - queryExecutor.writeToCopy(this, data, off, siz); - } - - public void flushCopy() throws SQLException { - queryExecutor.flushCopy(this); - } - - public long endCopy() throws SQLException { - return queryExecutor.endCopy(this); - } -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/CopyOperationImpl.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/CopyOperationImpl.java --- postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/CopyOperationImpl.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/CopyOperationImpl.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,66 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/core/v3/CopyOperationImpl.java,v 1.1 2009/07/01 05:00:40 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.core.v3; - -import java.sql.SQLException; - -import org.postgresql.copy.CopyOperation; -import org.postgresql.util.GT; -import org.postgresql.util.PSQLException; -import org.postgresql.util.PSQLState; - -public class CopyOperationImpl implements CopyOperation { - String sql; - QueryExecutorImpl queryExecutor; - int rowFormat; - int[] fieldFormats; - long handledRowCount = -1; - - void init(QueryExecutorImpl q, int fmt, int[] fmts) { - queryExecutor = q; - rowFormat = fmt; - fieldFormats = fmts; - } - - public void cancelCopy() throws SQLException { - queryExecutor.cancelCopy(this); - } - - public int getFieldCount() { - return fieldFormats.length; - } - - public int getFieldFormat(int field) { - return fieldFormats[field]; - } - - public int getFormat() { - return rowFormat; - } - - public boolean isActive() { - synchronized(queryExecutor) { - return queryExecutor.hasLock(this); - } - } - - public void handleCommandStatus(String status) throws PSQLException { - if(status.startsWith("COPY")) { - int i = status.lastIndexOf(' '); - handledRowCount = i > 3 ? Long.parseLong(status.substring( i + 1 )) : -1; - } else { - throw new PSQLException(GT.tr("CommandComplete expected COPY but got: " + status), PSQLState.COMMUNICATION_ERROR); - } - } - - public long getHandledRowCount() { - return handledRowCount; - } -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/CopyOutImpl.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/CopyOutImpl.java --- postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/CopyOutImpl.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/CopyOutImpl.java 1970-01-01 01:00:00.000000000 +0100 @@ -1,54 +0,0 @@ -/*------------------------------------------------------------------------- -* -* Copyright (c) 2009, PostgreSQL Global Development Group -* -* IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/core/v3/CopyOutImpl.java,v 1.1 2009/07/01 05:00:40 jurka Exp $ -* -*------------------------------------------------------------------------- -*/ -package org.postgresql.core.v3; - -import java.sql.SQLException; - -import org.postgresql.copy.CopyOut; - -/** - * Anticipated flow of a COPY TO STDOUT operation: - * - * CopyManager.copyOut() - * ->QueryExecutor.startCopy() - * - sends given query to server - * ->processCopyResults(): - * - receives CopyOutResponse from Server - * - creates new CopyOutImpl - * ->initCopy(): - * - receives copy metadata from server - * ->CopyOutImpl.init() - * ->lock() connection for this operation - * - if query fails an exception is thrown - * - if query returns wrong CopyOperation, copyOut() cancels it before throwing exception - * <-returned: new CopyOutImpl holding lock on connection - * repeat CopyOut.readFromCopy() until null - * ->CopyOutImpl.readFromCopy() - * ->QueryExecutorImpl.readFromCopy() - * ->processCopyResults() - * - on copydata row from server - * ->CopyOutImpl.handleCopydata() stores reference to byte array - * - on CopyDone, CommandComplete, ReadyForQuery - * ->unlock() connection for use by other operations - * <-returned: byte array of data received from server or null at end. - */ -public class CopyOutImpl extends CopyOperationImpl implements CopyOut { - private byte[] currentDataRow; - - public byte[] readFromCopy() throws SQLException { - currentDataRow = null; - queryExecutor.readFromCopy(this); - return currentDataRow; - } - - void handleCopydata(byte[] data) { - currentDataRow = data; - } -} diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/QueryExecutorImpl.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/QueryExecutorImpl.java --- postgresql-jdbc-8.4-701.src/org/postgresql/core/v3/QueryExecutorImpl.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/core/v3/QueryExecutorImpl.java 2009-07-01 23:23:24.000000000 +0200 @@ -26,7 +26,6 @@ import org.postgresql.util.PSQLState; import org.postgresql.util.ServerErrorMessage; import org.postgresql.util.GT; -import org.postgresql.copy.CopyOperation; /** * QueryExecutor implementation for the V3 protocol. @@ -689,355 +688,6 @@ return returnValue; } - // - // Copy subprotocol implementation - // - - /** - * Sends given query to BE to start, initialize and lock connection for a CopyOperation. - * @param sql COPY FROM STDIN / COPY TO STDOUT statement - * @return CopyIn or CopyOut operation object - * @throws SQLException on failure - */ - public synchronized CopyOperation startCopy(String sql) throws SQLException { - waitOnLock(); - byte buf[] = Utils.encodeUTF8(sql); - - try { - pgStream.SendChar('Q'); - pgStream.SendInteger4(buf.length + 4 + 1); - pgStream.Send(buf); - pgStream.SendChar(0); - pgStream.flush(); - - return processCopyResults(null, true); // expect a CopyInResponse or CopyOutResponse to our query above - } catch(IOException ioe) { - throw new PSQLException(GT.tr("Database connection failed when starting copy"), PSQLState.CONNECTION_FAILURE, ioe); - } - } - - /** - * Locks connection and calls initializer for a new CopyOperation - * Called via startCopy -> processCopyResults - * @param op an unitialized CopyOperation - * @throws SQLException on locking failure - * @throws IOException on database connection failure - */ - private synchronized void initCopy(CopyOperationImpl op) throws SQLException, IOException { - pgStream.ReceiveInteger4(); // length not used - int rowFormat = pgStream.ReceiveChar(); - int numFields = pgStream.ReceiveInteger2(); - int[] fieldFormats = new int[numFields]; - - for(int i=0; i CopyFail"); - } - final byte[] msg = Utils.encodeUTF8("Copy cancel requested"); - pgStream.SendChar('f'); // CopyFail - pgStream.SendInteger4(5 + msg.length); - pgStream.Send(msg); - pgStream.SendChar(0); - pgStream.flush(); - do { - try { - processCopyResults(op, true); // discard rest of input - } catch(SQLException se) { // expected error response to failing copy - errors++; - if( error != null ) { - SQLException e = se, next; - while( (next = e.getNextException()) != null ) - e = next; - e.setNextException(error); - } - error = se; - } - } while(hasLock(op)); - } - } else if (op instanceof CopyOutImpl) { - protoConnection.sendQueryCancel(); - } - - } catch(IOException ioe) { - throw new PSQLException(GT.tr("Database connection failed when canceling copy operation"), PSQLState.CONNECTION_FAILURE, ioe); - } - - if (op instanceof CopyInImpl) { - if(errors < 1) { - throw new PSQLException(GT.tr("Missing expected error response to copy cancel request"), PSQLState.COMMUNICATION_ERROR); - } else if(errors > 1) { - throw new PSQLException(GT.tr("Got {0} error responses to single copy cancel request", String.valueOf(errors)), PSQLState.COMMUNICATION_ERROR, error); - } - } - } - - /** - * Finishes writing to copy and unlocks connection - * @param op the copy operation presumably currently holding lock on this connection - * @return number of rows updated for server versions 8.2 or newer - * @throws SQLException on failure - */ - public synchronized long endCopy(CopyInImpl op) throws SQLException { - if(!hasLock(op)) - throw new PSQLException(GT.tr("Tried to end inactive copy"), PSQLState.OBJECT_NOT_IN_STATE); - - try { - pgStream.SendChar('c'); // CopyDone - pgStream.SendInteger4(4); - pgStream.flush(); - - processCopyResults(op, true); - return op.getHandledRowCount(); - } catch(IOException ioe) { - throw new PSQLException(GT.tr("Database connection failed when ending copy"), PSQLState.CONNECTION_FAILURE, ioe); - } - } - - /** - * Sends data during a live COPY IN operation. Only unlocks the connection if server - * suddenly returns CommandComplete, which should not happen - * @param op the CopyIn operation presumably currently holding lock on this connection - * @param data bytes to send - * @param off index of first byte to send (usually 0) - * @param siz number of bytes to send (usually data.length) - * @throws SQLException on failure - */ - public synchronized void writeToCopy(CopyInImpl op, byte[] data, int off, int siz) throws SQLException { - if(!hasLock(op)) - throw new PSQLException(GT.tr("Tried to write to an inactive copy operation"), PSQLState.OBJECT_NOT_IN_STATE); - - if (logger.logDebug()) - logger.debug(" FE=> CopyData(" + (siz-off) + ")"); - - try { - pgStream.SendChar('d'); - pgStream.SendInteger4(siz + 4); - pgStream.Send(data, off, siz); - - processCopyResults(op, false); // collect any pending notifications without blocking - } catch(IOException ioe) { - throw new PSQLException(GT.tr("Database connection failed when writing to copy"), PSQLState.CONNECTION_FAILURE, ioe); - } - } - - public synchronized void flushCopy(CopyInImpl op) throws SQLException { - if(!hasLock(op)) - throw new PSQLException(GT.tr("Tried to write to an inactive copy operation"), PSQLState.OBJECT_NOT_IN_STATE); - - try { - pgStream.flush(); - processCopyResults(op, false); // collect any pending notifications without blocking - } catch(IOException ioe) { - throw new PSQLException(GT.tr("Database connection failed when writing to copy"), PSQLState.CONNECTION_FAILURE, ioe); - } - } - - /** - * Blocks to wait for a row of data to be received from server on an active copy operation - * Connection gets unlocked by processCopyResults() at end of operation - * @param op the copy operation presumably currently holding lock on this connection - * @throws SQLException on any failure - */ - synchronized void readFromCopy(CopyOutImpl op) throws SQLException { - if(!hasLock(op)) - throw new PSQLException(GT.tr("Tried to read from inactive copy"), PSQLState.OBJECT_NOT_IN_STATE); - - try { - processCopyResults(op, true); // expect a call to handleCopydata() to store the data - } catch(IOException ioe) { - throw new PSQLException(GT.tr("Database connection failed when reading from copy"), PSQLState.CONNECTION_FAILURE, ioe); - } - } - - /** - * Handles copy sub protocol responses from server. - * Unlocks at end of sub protocol, - * so operations on pgStream or QueryExecutor are not allowed in a method after calling this! - * @param block whether to block waiting for input - * @return - * CopyIn when COPY FROM STDIN starts; - * CopyOut when COPY TO STDOUT starts; - * null when copy ends; - * otherwise, the operation given as parameter. - * @throws SQLException in case of misuse - * @throws IOException from the underlying connection - */ - CopyOperationImpl processCopyResults(CopyOperationImpl op, boolean block) throws SQLException, IOException { - - boolean endReceiving = false; - SQLException error = null, errors = null; - int len; - - while( !endReceiving && (block || pgStream.hasMessagePending()) ) { - int c = pgStream.ReceiveChar(); - switch(c) { - - case 'A': // Asynchronous Notify - - if (logger.logDebug()) - logger.debug(" <=BE Asynchronous Notification while copying"); - - receiveAsyncNotify(); - break; - - case 'N': // Notice Response - - if (logger.logDebug()) - logger.debug(" <=BE Notification while copying"); - - protoConnection.addWarning(receiveNoticeResponse()); - break; - - case 'C': // Command Complete - - String status = receiveCommandStatus(); - - try { - if(op == null) - throw new PSQLException(GT.tr("Received CommandComplete ''{0}'' without an active copy operation", status), PSQLState.OBJECT_NOT_IN_STATE); - op.handleCommandStatus(status); - } catch(SQLException se) { - error = se; - } - - block = true; - break; - - case 'E': // ErrorMessage (expected response to CopyFail) - - error = receiveErrorResponse(); - // We've received the error and we now expect to receive - // Ready for query, but we must block because it might still be - // on the wire and not here yet. - block = true; - break; - - case 'G': // CopyInResponse - - if (logger.logDebug()) - logger.debug(" <=BE CopyInResponse"); - - if(op != null) - error = new PSQLException(GT.tr("Got CopyInResponse from server during an active {0}", op.getClass().getName()), PSQLState.OBJECT_NOT_IN_STATE); - - op = new CopyInImpl(); - initCopy(op); - endReceiving = true; - break; - - case 'H': // CopyOutResponse - - if (logger.logDebug()) - logger.debug(" <=BE CopyOutResponse"); - - if(op != null) - error = new PSQLException(GT.tr("Got CopyOutResponse from server during an active {0}", op.getClass().getName()), PSQLState.OBJECT_NOT_IN_STATE); - - op = new CopyOutImpl(); - initCopy(op); - endReceiving = true; - break; - - case 'd': // CopyData - - if (logger.logDebug()) - logger.debug(" <=BE CopyData"); - - len = pgStream.ReceiveInteger4() - 4; - byte[] buf = pgStream.Receive(len); - if(op == null) { - error = new PSQLException(GT.tr("Got CopyData without an active copy operation"), PSQLState.OBJECT_NOT_IN_STATE); - } else if (!(op instanceof CopyOutImpl)) { - error = new PSQLException(GT.tr("Unexpected copydata from server for {0}", - op == null ? "null" : op.getClass().getName()), PSQLState.COMMUNICATION_ERROR); - } else { - ((CopyOutImpl)op).handleCopydata(buf); - } - endReceiving = true; - break; - - case 'c': // CopyDone (expected after all copydata received) - - if (logger.logDebug()) - logger.debug(" <=BE CopyDone"); - - len = pgStream.ReceiveInteger4() - 4; - if(len > 0) - pgStream.Receive(len); // not in specification; should never appear - - if(!(op instanceof CopyOutImpl)) - error = new PSQLException("Got CopyDone while not copying from server", PSQLState.OBJECT_NOT_IN_STATE); - - // keep receiving since we expect a CommandComplete - block = true; - break; - - case 'Z': // ReadyForQuery: After FE:CopyDone => BE:CommandComplete - - receiveRFQ(); - if(hasLock(op)) - unlock(op); - op = null; - endReceiving = true; - break; - - // If the user sends a non-copy query, we've got to handle some additional things. - // - case 'T': // Row Description (response to Describe) - if (logger.logDebug()) - logger.debug(" <=BE RowDescription (during copy ignored)"); - - - skipMessage(); - break; - - case 'D': // DataRow - if (logger.logDebug()) - logger.debug(" <=BE DataRow (during copy ignored)"); - - skipMessage(); - break; - - default: - throw new IOException(GT.tr("Unexpected packet type during copy: {0}", Integer.toString(c))); - } - - // Collect errors into a neat chain for completeness - if(error != null) { - if(errors != null) - error.setNextException(errors); - errors = error; - error = null; - } - } - - if(errors != null) - throw errors; - - return op; - } - /* * Send a query to the backend. */ diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/jdbc2/AbstractJdbc2Connection.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/jdbc2/AbstractJdbc2Connection.java --- postgresql-jdbc-8.4-701.src/org/postgresql/jdbc2/AbstractJdbc2Connection.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/jdbc2/AbstractJdbc2Connection.java 2009-07-01 23:23:24.000000000 +0200 @@ -22,7 +22,6 @@ import org.postgresql.util.PGobject; import org.postgresql.util.PSQLException; import org.postgresql.util.GT; -import org.postgresql.copy.*; /** * This class defines methods of the jdbc2 specification. @@ -1060,12 +1059,4 @@ { return bindStringAsVarchar; } - - private CopyManager copyManager = null; - public CopyManager getCopyAPI() throws SQLException - { - if (copyManager == null) - copyManager = new CopyManager(this); - return copyManager; - } } diff -ruN postgresql-jdbc-8.4-701.src/org/postgresql/test/jdbc2/CopyTest.java postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/test/jdbc2/CopyTest.java --- postgresql-jdbc-8.4-701.src/org/postgresql/test/jdbc2/CopyTest.java 2009-07-01 07:00:40.000000000 +0200 +++ postgresql-jdbc-8.4-701.src_without_CopyManager/org/postgresql/test/jdbc2/CopyTest.java 2008-01-28 11:08:58.000000000 +0100 @@ -3,258 +3,87 @@ * Copyright (c) 2008, PostgreSQL Global Development Group * * IDENTIFICATION -* $PostgreSQL: pgjdbc/org/postgresql/test/jdbc2/CopyTest.java,v 1.2 2009/07/01 05:00:40 jurka Exp $ +* $PostgreSQL: pgjdbc/org/postgresql/test/jdbc2/CopyTest.java,v 1.1 2008/01/28 10:08:58 jurka Exp $ * *------------------------------------------------------------------------- */ -package org.postgresql.test.jdbc2; - -import java.sql.Connection; -import java.sql.ResultSet; -import java.sql.SQLException; -import java.sql.Statement; -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.InputStream; -import java.io.OutputStream; -import java.io.PrintStream; -import java.io.IOException; -import junit.framework.TestCase; +package org.postgresql.test.jdbc2; -import org.postgresql.PGConnection; -import org.postgresql.copy.*; import org.postgresql.test.TestUtil; -import org.postgresql.util.PSQLState; +import junit.framework.TestCase; +import java.sql.*; /** - * @author kato@iki.fi - * + * Even though the driver doesn't support the copy protocol, if a user + * issues a copy command, the driver shouldn't destroy the whole connection. */ -public class CopyTest extends TestCase { - - private Connection con; - private CopyManager copyAPI; - private String[] origData = - { "First Row\t1\t1.10\n", // 0's required to match DB output for numeric(5,2) - "Second Row\t2\t-22.20\n", - "\\N\t\\N\t\\N\n", - "\t4\t444.40\n" }; - private int dataRows = origData.length; - - public CopyTest(String name) { - super(name); - } - - private byte[] getData(String[] origData) { - ByteArrayOutputStream buf = new ByteArrayOutputStream(); - PrintStream ps = new PrintStream(buf); - for(int i=0; i 0) { - at = "buffering"; - InputStream ins = new ByteArrayInputStream(getData(origData)); - at = "skipping"; - ins.skip(skip++); - skipChar = ins.read(); - at = "copying"; - copyAPI.copyIn(sql, ins, 3); - at = "using connection after writing copy"; - rowCount = getCount(); - } - } catch(Exception e) { - if( !( skipChar=='\t' ) ) // error expected when field separator consumed - fail("testSkipping at " + at + " round " + skip + ": " + e.toString()); - } - assertEquals(dataRows*(skip-1), rowCount); - } +public class CopyTest extends TestCase +{ + private Connection conn; - public void testCopyOutByRow() throws SQLException, IOException { - testCopyInByRow(); // ensure we have some data. - String sql = "COPY copytest TO STDOUT"; - CopyOut cp = copyAPI.copyOut(sql); - int count = 0; - byte buf[]; - while ( (buf = cp.readFromCopy()) != null) { - count++; - } - assertEquals(false, cp.isActive()); - assertEquals(dataRows, count); - - long rowCount = cp.getHandledRowCount(); - long expectedResult = -1; - if (TestUtil.haveMinimumServerVersion(con, "8.2")) { - expectedResult = dataRows; - } - assertEquals(expectedResult, rowCount); - - assertEquals(dataRows, getCount()); + public CopyTest(String name) + { + super(name); } - public void testCopyOut() throws SQLException, IOException { - testCopyInByRow(); // ensure we have some data. - String sql = "COPY copytest TO STDOUT"; - ByteArrayOutputStream copydata = new ByteArrayOutputStream(); - copyAPI.copyOut(sql, copydata); - assertEquals(dataRows, getCount()); - // deep comparison of data written and read - byte[] copybytes = copydata.toByteArray(); - assertTrue(copybytes != null); - for(int i=0, l=0; i= l + origBytes.length); - for(int j=0; j