Package com.mysql.jdbc

Source Code of com.mysql.jdbc.RowDataDynamic

/*
Copyright (c) 2002, 2013, Oracle and/or its affiliates. All rights reserved.

  The MySQL Connector/J is licensed under the terms of the GPLv2
  <http://www.gnu.org/licenses/old-licenses/gpl-2.0.html>, like most MySQL Connectors.
  There are special exceptions to the terms and conditions of the GPLv2 as it is applied to
  this software, see the FLOSS License Exception
  <http://www.mysql.com/about/legal/licensing/foss-exception.html>.

  This program is free software; you can redistribute it and/or modify it under the terms
  of the GNU General Public License as published by the Free Software Foundation; version 2
  of the License.

  This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
  without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  See the GNU General Public License for more details.

  You should have received a copy of the GNU General Public License along with this
  program; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth
  Floor, Boston, MA 02110-1301  USA



*/
package com.mysql.jdbc;

import java.sql.SQLException;

import com.mysql.jdbc.exceptions.MySQLQueryInterruptedException;
import com.mysql.jdbc.profiler.ProfilerEvent;
import com.mysql.jdbc.profiler.ProfilerEventHandler;

/**
* Allows streaming of MySQL data.
*
* @author dgan
* @version $Id$
*/
public class RowDataDynamic implements RowData {

  class OperationNotSupportedException extends SQLException {

    static final long serialVersionUID = 5582227030787355276L;

    OperationNotSupportedException() {
      super(
          Messages.getString("RowDataDynamic.10"), SQLError.SQL_STATE_ILLEGAL_ARGUMENT); //$NON-NLS-1$
    }
  }

  private int columnCount;

  private Field[] metadata;

  private int index = -1;

  private MysqlIO io;

  private boolean isAfterEnd = false;

  private boolean noMoreRows = false;

  private boolean isBinaryEncoded = false;

  private ResultSetRow nextRow;

  private ResultSetImpl owner;

  private boolean streamerClosed = false;
 
  private boolean wasEmpty = false; // we don't know until we attempt to traverse

  private boolean useBufferRowExplicit;

  private boolean moreResultsExisted;

  private ExceptionInterceptor exceptionInterceptor;

  private boolean isInterrupted = false;
 
  /**
   * Creates a new RowDataDynamic object.
   *
   * @param io
   *            the connection to MySQL that this data is coming from
   * @param metadata
   *            the metadata that describe this data
   * @param isBinaryEncoded
   *            is this data in native format?
   * @param colCount
   *            the number of columns
   * @throws SQLException
   *             if the next record can not be found
   */
  public RowDataDynamic(MysqlIO io, int colCount, Field[] fields,
      boolean isBinaryEncoded) throws SQLException {
    this.io = io;
    this.columnCount = colCount;
    this.isBinaryEncoded = isBinaryEncoded;
    this.metadata = fields;
    this.exceptionInterceptor = this.io.getExceptionInterceptor();
    this.useBufferRowExplicit = MysqlIO.useBufferRowExplicit(this.metadata);
  }

  /**
   * Adds a row to this row data.
   *
   * @param row
   *            the row to add
   * @throws SQLException
   *             if a database error occurs
   */
  public void addRow(ResultSetRow row) throws SQLException {
    notSupported();
  }

  /**
   * Moves to after last.
   *
   * @throws SQLException
   *             if a database error occurs
   */
  public void afterLast() throws SQLException {
    notSupported();
  }

  /**
   * Moves to before first.
   *
   * @throws SQLException
   *             if a database error occurs
   */
  public void beforeFirst() throws SQLException {
    notSupported();
  }

  /**
   * Moves to before last so next el is the last el.
   *
   * @throws SQLException
   *             if a database error occurs
   */
  public void beforeLast() throws SQLException {
    notSupported();
  }

  /**
   * We're done.
   *
   * @throws SQLException
   *             if a database error occurs
   */
  public void close() throws SQLException {
    // Belt and suspenders here - if we don't
    // have a reference to the connection
    // it's more than likely dead/gone and we
    // won't be able to consume rows anyway

    Object mutex = this;

    MySQLConnection conn = null;

    if (this.owner != null) {
      conn = this.owner.connection;

      if (conn != null) {
        mutex = conn.getConnectionMutex();
      }
    }

    boolean hadMore = false;
    int howMuchMore = 0;

    synchronized (mutex) {
      // drain the rest of the records.
      while (next() != null) {
        hadMore = true;
        howMuchMore++;

        if (howMuchMore % 100 == 0) {
          Thread.yield();
        }
      }

      if (conn != null) {
        if (!conn.getClobberStreamingResults() &&
            conn.getNetTimeoutForStreamingResults() > 0) {
          String oldValue = conn
          .getServerVariable("net_write_timeout");

          if (oldValue == null || oldValue.length() == 0) {
            oldValue = "60"; // the current default
          }

          this.io.clearInputStream();
         
          java.sql.Statement stmt = null;
         
          try {
            stmt = conn.createStatement();
            ((com.mysql.jdbc.StatementImpl)stmt).executeSimpleNonQuery(conn, "SET net_write_timeout=" + oldValue);
          } finally {
            if (stmt != null) {
              stmt.close();
            }
          }
        }
       
        if (conn.getUseUsageAdvisor()) {
          if (hadMore) {

            ProfilerEventHandler eventSink = ProfilerEventHandlerFactory
            .getInstance(conn);

            eventSink
            .consumeEvent(new ProfilerEvent(
                ProfilerEvent.TYPE_WARN,
                "", //$NON-NLS-1$
                this.owner.owningStatement == null ? "N/A" : this.owner.owningStatement.currentCatalog, //$NON-NLS-1$
                this.owner.connectionId,
                this.owner.owningStatement == null ? -1
                    : this.owner.owningStatement
                        .getId(),
                -1,
                System.currentTimeMillis(),
                0,
                Constants.MILLIS_I18N,
                null,
                null,
                Messages.getString("RowDataDynamic.2") //$NON-NLS-1$
                    + howMuchMore
                    + Messages
                        .getString("RowDataDynamic.3") //$NON-NLS-1$
                    + Messages
                        .getString("RowDataDynamic.4") //$NON-NLS-1$
                    + Messages
                        .getString("RowDataDynamic.5") //$NON-NLS-1$
                    + Messages
                        .getString("RowDataDynamic.6") //$NON-NLS-1$
                    + this.owner.pointOfOrigin));
          }
        }
      }
    }

    this.metadata = null;
    this.owner = null;
  }

  /**
   * Only works on non dynamic result sets.
   *
   * @param index
   *            row number to get at
   * @return row data at index
   * @throws SQLException
   *             if a database error occurs
   */
  public ResultSetRow getAt(int ind) throws SQLException {
    notSupported();

    return null;
  }

  /**
   * Returns the current position in the result set as a row number.
   *
   * @return the current row number
   * @throws SQLException
   *             if a database error occurs
   */
  public int getCurrentRowNumber() throws SQLException {
    notSupported();

    return -1;
  }

  /**
   * @see com.mysql.jdbc.RowData#getOwner()
   */
  public ResultSetInternalMethods getOwner() {
    return this.owner;
  }

  /**
   * Returns true if another row exsists.
   *
   * @return true if more rows
   * @throws SQLException
   *             if a database error occurs
   */
  public boolean hasNext() throws SQLException {
    boolean hasNext = (this.nextRow != null);

    if (!hasNext && !this.streamerClosed) {
      this.io.closeStreamer(this);
      this.streamerClosed = true;
    }

    return hasNext;
  }

  /**
   * Returns true if we got the last element.
   *
   * @return true if after last row
   * @throws SQLException
   *             if a database error occurs
   */
  public boolean isAfterLast() throws SQLException {
    return this.isAfterEnd;
  }

  /**
   * Returns if iteration has not occured yet.
   *
   * @return true if before first row
   * @throws SQLException
   *             if a database error occurs
   */
  public boolean isBeforeFirst() throws SQLException {
    return this.index < 0;
  }

  /**
   * Returns true if the result set is dynamic.
   *
   * This means that move back and move forward won't work because we do not
   * hold on to the records.
   *
   * @return true if this result set is streaming from the server
   */
  public boolean isDynamic() {
    return true;
  }

  /**
   * Has no records.
   *
   * @return true if no records
   * @throws SQLException
   *             if a database error occurs
   */
  public boolean isEmpty() throws SQLException {
    notSupported();

    return false;
  }

  /**
   * Are we on the first row of the result set?
   *
   * @return true if on first row
   * @throws SQLException
   *             if a database error occurs
   */
  public boolean isFirst() throws SQLException {
    notSupported();

    return false;
  }

  /**
   * Are we on the last row of the result set?
   *
   * @return true if on last row
   * @throws SQLException
   *             if a database error occurs
   */
  public boolean isLast() throws SQLException {
    notSupported();

    return false;
  }

  /**
   * Moves the current position relative 'rows' from the current position.
   *
   * @param rows
   *            the relative number of rows to move
   * @throws SQLException
   *             if a database error occurs
   */
  public void moveRowRelative(int rows) throws SQLException {
    notSupported();
  }

  /**
   * Returns the next row.
   *
   * @return the next row value
   * @throws SQLException
   *             if a database error occurs
   */
  public ResultSetRow next() throws SQLException {
   

    nextRecord();

    if (this.nextRow == null && !this.streamerClosed && !this.moreResultsExisted) {
      this.io.closeStreamer(this);
      this.streamerClosed = true;
    }
   
    if (this.nextRow != null) {
      if (this.index != Integer.MAX_VALUE) {
        this.index++;
      }
    }
   
    return this.nextRow;
  }


  private void nextRecord() throws SQLException {

    try {
      if (!this.noMoreRows) {       
        this.nextRow = isInterrupted ? null :
            this.io.nextRow(this.metadata, this.columnCount,
            this.isBinaryEncoded,
            java.sql.ResultSet.CONCUR_READ_ONLY, true,
            this.useBufferRowExplicit, true, null);

        if (this.nextRow == null) {
          this.noMoreRows = true;
          this.isAfterEnd = true;
          this.moreResultsExisted = this.io.tackOnMoreStreamingResults(this.owner);

          if (this.index == -1) {
            this.wasEmpty = true;
          }
        }
      } else {
        this.isAfterEnd = true;
      }
    } catch (SQLException sqlEx) {
      if (sqlEx instanceof StreamingNotifiable) {
        ((StreamingNotifiable)sqlEx).setWasStreamingResults();
      } else if (sqlEx instanceof MySQLQueryInterruptedException) {
        this.isInterrupted = true;
      }
     
      // don't wrap SQLExceptions
      throw sqlEx;
    } catch (Exception ex) {
      String exceptionType = ex.getClass().getName();
      String exceptionMessage = ex.getMessage();

      exceptionMessage += Messages.getString("RowDataDynamic.7"); //$NON-NLS-1$
      exceptionMessage += Util.stackTraceToString(ex);

      SQLException sqlEx = SQLError.createSQLException(
          Messages.getString("RowDataDynamic.8") //$NON-NLS-1$
              + exceptionType
              + Messages.getString("RowDataDynamic.9") + exceptionMessage, SQLError.SQL_STATE_GENERAL_ERROR, this.exceptionInterceptor); //$NON-NLS-1$
      sqlEx.initCause(ex);
     
      throw sqlEx;
    }
  }

  private void notSupported() throws SQLException {
    throw new OperationNotSupportedException();
  }

  /**
   * Removes the row at the given index.
   *
   * @param index
   *            the row to move to
   * @throws SQLException
   *             if a database error occurs
   */
  public void removeRow(int ind) throws SQLException {
    notSupported();
  }

  /**
   * Moves the current position in the result set to the given row number.
   *
   * @param rowNumber
   *            row to move to
   * @throws SQLException
   *             if a database error occurs
   */
  public void setCurrentRow(int rowNumber) throws SQLException {
    notSupported();
  }

  /**
   * @see com.mysql.jdbc.RowData#setOwner(com.mysql.jdbc.ResultSetInternalMethods)
   */
  public void setOwner(ResultSetImpl rs) {
    this.owner = rs;
  }

  /**
   * Only works on non dynamic result sets.
   *
   * @return the size of this row data
   */
  public int size() {
    return RESULT_SET_SIZE_UNKNOWN;
  }

  public boolean wasEmpty() {
    return this.wasEmpty;
  }

  public void setMetadata(Field[] metadata) {
    this.metadata = metadata;
  }
}
TOP

Related Classes of com.mysql.jdbc.RowDataDynamic

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.
r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o), m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m) })(window,document,'script','//www.google-analytics.com/analytics.js','ga'); ga('create', 'UA-20639858-1', 'auto'); ga('send', 'pageview');