You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@phoenix.apache.org by "Kevin Liew (JIRA)" <ji...@apache.org> on 2016/01/08 21:52:39 UTC

[jira] [Updated] (PHOENIX-2583) Phoenix queryserver sends result set in response to the wrong request

     [ https://issues.apache.org/jira/browse/PHOENIX-2583?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel ]

Kevin Liew updated PHOENIX-2583:
--------------------------------
    Description: 
Create two tables

{code:sql}
DROP TABLE IF EXISTS SEN.VARCHAR_TABLE;
CREATE TABLE IF NOT EXISTS SEN.VARCHAR_TABLE(
	KeyColumn VARCHAR(255) PRIMARY KEY,
	Column1 VARCHAR(510));

UPSERT INTO SEN.VARCHAR_TABLE VALUES ("One","1");
{code}
{code:sql}
DROP TABLE IF EXISTS SEN.INTEGER_TABLE;
CREATE TABLE IF NOT EXISTS SEN.INTEGER_TABLE(
	KeyColumn VARCHAR(255) PRIMARY KEY,
	Column1 INTEGER);

UPSERT INTO SEN.VARCHAR_TABLE VALUES ("Two",2);
{code}

Running these two programs results in several crashes. 

1. select a varchar by parameterized statement resulting in
SELECT Column1 FROM SEN.VARCHAR_TABLE WHERE KeyColumn = 'One'
{code:java}
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.PreparedStatement;
import java.sql.Statement;

public class Hello_World {
	public static void main(String[] args) throws SQLException {
		try {
            Class.forName("org.apache.phoenix.queryserver.client.Driver");
        } catch (ClassNotFoundException e) {
            System.out.println("Where is your PhoenixDriver");
            e.printStackTrace();
            return;
        }

		Connection conn = DriverManager.getConnection("jdbc:phoenix:thin:url=http://192.168.222.52:8765");
		conn.setAutoCommit(true);

		String sqlStmt = "SELECT Column1 FROM SEN.VARCHAR_TABLE WHERE KeyColumn = ?";
		System.out.println("SQL Statement:\n\t" + sqlStmt);
		
		while(true)
		{
			ResultSet rset = null;
	
			//Statement stmt = conn.createStatement();
			PreparedStatement stmt = conn.prepareStatement(sqlStmt);
			stmt.setString(1, "One");
			ResultSet rs = stmt.executeQuery();
      
			while (rs.next()) {
		    	String column1 = rs.getString("column1");
		    	if (!column1.equals("1"))
		    	{
		    		System.out.println(column1);
		    	}
			}
		}
		
        //conn.close();
	}
	
}
{code}

2. select an integer by parameterized statement resulting in
SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = 'Two'
{code:java}
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.PreparedStatement;
import java.sql.Statement;



public class Hello_World {
	public static void main(String[] args) throws SQLException {
		try {
            Class.forName("org.apache.phoenix.queryserver.client.Driver");
        } catch (ClassNotFoundException e) {
            System.out.println("Where is your PhoenixDriver");
            e.printStackTrace();
            return;
        }

		Connection conn = DriverManager.getConnection("jdbc:phoenix:thin:url=http://192.168.222.52:8765");
		conn.setAutoCommit(true);
		
		String sqlStmt = "SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = ?";
		System.out.println("SQL Statement:\n\t" + sqlStmt);
		
		while(true)
		{
			ResultSet rset = null;
	
			//Statement stmt = conn.createStatement();
			PreparedStatement stmt = conn.prepareStatement(sqlStmt);
			stmt.setString(1, "Two");
			ResultSet rs = stmt.executeQuery();
      
			while (rs.next()) {
		    	int column1 = rs.getInt("column1");
		    	if (column1 != 2)
		    	{
		    		System.out.println(column1);
		    	}
			}
		}
		
        //conn.close();
	}
	
}

{code}

There are several crashes (might be preventable by adding a pause in the loops?), but the one relevant to this bug is:
{code:java}
SQL Statement:
	SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = ?
Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Number
	at org.apache.calcite.avatica.util.AbstractCursor$NumberAccessor.getNumber(AbstractCursor.java:661)
	at org.apache.calcite.avatica.util.AbstractCursor$BigNumberAccessor.getInt(AbstractCursor.java:602)
	at org.apache.calcite.avatica.AvaticaResultSet.getInt(AvaticaResultSet.java:314)
	at Hello_World.main(Hello_World.java:36)

{code}
where we get a string from SEN.VARCHAR_TABLE while we are querying from the SEN.INTEGER_TABLE.

The queryserver is sending the result set in response to a request made from another connection id. The statement id was not checked but there may have been a statement id collision

  was:
Create two tables

{code:sql}
DROP TABLE IF EXISTS SEN.VARCHAR_TABLE;
CREATE TABLE IF NOT EXISTS SEN.VARCHAR_TABLE(
	KeyColumn VARCHAR(255) PRIMARY KEY,
	Column1 VARCHAR(510));

UPSERT INTO SEN.VARCHAR_TABLE VALUES ("One","1");
{code}
{code:sql}
DROP TABLE IF EXISTS SEN.INTEGER_TABLE;
CREATE TABLE IF NOT EXISTS SEN.INTEGER_TABLE(
	KeyColumn VARCHAR(255) PRIMARY KEY,
	Column1 INTEGER);

UPSERT INTO SEN.VARCHAR_TABLE VALUES ("Two",2);
{code}

Running these two programs results in several crashes. 

1. select a varchar by parameterized statement resulting in
SELECT Column1 FROM SEN.VARCHAR_TABLE WHERE KeyColumn = 'One'
{code:java}
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.PreparedStatement;
import java.sql.Statement;

public class Hello_World {
	public static void main(String[] args) throws SQLException {
		try {
            Class.forName("org.apache.phoenix.queryserver.client.Driver");
        } catch (ClassNotFoundException e) {
            System.out.println("Where is your PhoenixDriver");
            e.printStackTrace();
            return;
        }

		Connection conn = DriverManager.getConnection("jdbc:phoenix:thin:url=http://192.168.222.52:8765");
		conn.setAutoCommit(true);

		String sqlStmt = "SELECT Column1 FROM SEN.VARCHAR_TABLE WHERE KeyColumn = ?";
		System.out.println("SQL Statement:\n\t" + sqlStmt);
		
		while(true)
		{
			ResultSet rset = null;
	
			//Statement stmt = conn.createStatement();
			PreparedStatement stmt = conn.prepareStatement(sqlStmt);
			stmt.setString(1, "One");
			ResultSet rs = stmt.executeQuery();
      
			while (rs.next()) {
		    	String column1 = rs.getString("column1");
		    	if (!column1.equals("1"))
		    	{
		    		System.out.println(column1);
		    	}
			}
		}
		
        //conn.close();
	}
	
}
{code}

2. select an integer by parameterized statement resulting in
SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = 'Two'
{code:java}
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.PreparedStatement;
import java.sql.Statement;



public class Hello_World {
	public static void main(String[] args) throws SQLException {
		try {
            Class.forName("org.apache.phoenix.queryserver.client.Driver");
        } catch (ClassNotFoundException e) {
            System.out.println("Where is your PhoenixDriver");
            e.printStackTrace();
            return;
        }

		Connection conn = DriverManager.getConnection("jdbc:phoenix:thin:url=http://192.168.222.52:8765");
		conn.setAutoCommit(true);
		
		String sqlStmt = "SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = ?";
		System.out.println("SQL Statement:\n\t" + sqlStmt);
		
		while(true)
		{
			ResultSet rset = null;
	
			//Statement stmt = conn.createStatement();
			PreparedStatement stmt = conn.prepareStatement(sqlStmt);
			stmt.setString(1, "Two");
			ResultSet rs = stmt.executeQuery();
      
			while (rs.next()) {
		    	int column1 = rs.getInt("column1");
		    	if (column1 != 2)
		    	{
		    		System.out.println(column1);
		    	}
			}
		}
		
        //conn.close();
	}
	
}

{code}

There are several crashes, but the one relevant to this bug is:
{code:java}
SQL Statement:
	SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = ?
Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Number
	at org.apache.calcite.avatica.util.AbstractCursor$NumberAccessor.getNumber(AbstractCursor.java:661)
	at org.apache.calcite.avatica.util.AbstractCursor$BigNumberAccessor.getInt(AbstractCursor.java:602)
	at org.apache.calcite.avatica.AvaticaResultSet.getInt(AvaticaResultSet.java:314)
	at Hello_World.main(Hello_World.java:36)

{code}

The queryserver is sending the result set in response to a request made from another connection id. The statement id was not checked but there may have been a statement id collision


> Phoenix queryserver sends result set in response to the wrong request
> ---------------------------------------------------------------------
>
>                 Key: PHOENIX-2583
>                 URL: https://issues.apache.org/jira/browse/PHOENIX-2583
>             Project: Phoenix
>          Issue Type: Bug
>    Affects Versions: 4.6.0
>            Reporter: Kevin Liew
>            Priority: Critical
>              Labels: phoenix, queryserver
>
> Create two tables
> {code:sql}
> DROP TABLE IF EXISTS SEN.VARCHAR_TABLE;
> CREATE TABLE IF NOT EXISTS SEN.VARCHAR_TABLE(
> 	KeyColumn VARCHAR(255) PRIMARY KEY,
> 	Column1 VARCHAR(510));
> UPSERT INTO SEN.VARCHAR_TABLE VALUES ("One","1");
> {code}
> {code:sql}
> DROP TABLE IF EXISTS SEN.INTEGER_TABLE;
> CREATE TABLE IF NOT EXISTS SEN.INTEGER_TABLE(
> 	KeyColumn VARCHAR(255) PRIMARY KEY,
> 	Column1 INTEGER);
> UPSERT INTO SEN.VARCHAR_TABLE VALUES ("Two",2);
> {code}
> Running these two programs results in several crashes. 
> 1. select a varchar by parameterized statement resulting in
> SELECT Column1 FROM SEN.VARCHAR_TABLE WHERE KeyColumn = 'One'
> {code:java}
> import java.sql.Connection;
> import java.sql.DriverManager;
> import java.sql.ResultSet;
> import java.sql.SQLException;
> import java.sql.PreparedStatement;
> import java.sql.Statement;
> public class Hello_World {
> 	public static void main(String[] args) throws SQLException {
> 		try {
>             Class.forName("org.apache.phoenix.queryserver.client.Driver");
>         } catch (ClassNotFoundException e) {
>             System.out.println("Where is your PhoenixDriver");
>             e.printStackTrace();
>             return;
>         }
> 		Connection conn = DriverManager.getConnection("jdbc:phoenix:thin:url=http://192.168.222.52:8765");
> 		conn.setAutoCommit(true);
> 		String sqlStmt = "SELECT Column1 FROM SEN.VARCHAR_TABLE WHERE KeyColumn = ?";
> 		System.out.println("SQL Statement:\n\t" + sqlStmt);
> 		
> 		while(true)
> 		{
> 			ResultSet rset = null;
> 	
> 			//Statement stmt = conn.createStatement();
> 			PreparedStatement stmt = conn.prepareStatement(sqlStmt);
> 			stmt.setString(1, "One");
> 			ResultSet rs = stmt.executeQuery();
>       
> 			while (rs.next()) {
> 		    	String column1 = rs.getString("column1");
> 		    	if (!column1.equals("1"))
> 		    	{
> 		    		System.out.println(column1);
> 		    	}
> 			}
> 		}
> 		
>         //conn.close();
> 	}
> 	
> }
> {code}
> 2. select an integer by parameterized statement resulting in
> SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = 'Two'
> {code:java}
> import java.sql.Connection;
> import java.sql.DriverManager;
> import java.sql.ResultSet;
> import java.sql.SQLException;
> import java.sql.PreparedStatement;
> import java.sql.Statement;
> public class Hello_World {
> 	public static void main(String[] args) throws SQLException {
> 		try {
>             Class.forName("org.apache.phoenix.queryserver.client.Driver");
>         } catch (ClassNotFoundException e) {
>             System.out.println("Where is your PhoenixDriver");
>             e.printStackTrace();
>             return;
>         }
> 		Connection conn = DriverManager.getConnection("jdbc:phoenix:thin:url=http://192.168.222.52:8765");
> 		conn.setAutoCommit(true);
> 		
> 		String sqlStmt = "SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = ?";
> 		System.out.println("SQL Statement:\n\t" + sqlStmt);
> 		
> 		while(true)
> 		{
> 			ResultSet rset = null;
> 	
> 			//Statement stmt = conn.createStatement();
> 			PreparedStatement stmt = conn.prepareStatement(sqlStmt);
> 			stmt.setString(1, "Two");
> 			ResultSet rs = stmt.executeQuery();
>       
> 			while (rs.next()) {
> 		    	int column1 = rs.getInt("column1");
> 		    	if (column1 != 2)
> 		    	{
> 		    		System.out.println(column1);
> 		    	}
> 			}
> 		}
> 		
>         //conn.close();
> 	}
> 	
> }
> {code}
> There are several crashes (might be preventable by adding a pause in the loops?), but the one relevant to this bug is:
> {code:java}
> SQL Statement:
> 	SELECT Column1 FROM SEN.INTEGER_TABLE WHERE KeyColumn = ?
> Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Number
> 	at org.apache.calcite.avatica.util.AbstractCursor$NumberAccessor.getNumber(AbstractCursor.java:661)
> 	at org.apache.calcite.avatica.util.AbstractCursor$BigNumberAccessor.getInt(AbstractCursor.java:602)
> 	at org.apache.calcite.avatica.AvaticaResultSet.getInt(AvaticaResultSet.java:314)
> 	at Hello_World.main(Hello_World.java:36)
> {code}
> where we get a string from SEN.VARCHAR_TABLE while we are querying from the SEN.INTEGER_TABLE.
> The queryserver is sending the result set in response to a request made from another connection id. The statement id was not checked but there may have been a statement id collision



--
This message was sent by Atlassian JIRA
(v6.3.4#6332)