Search in sources :

Example 1 with ParseMessage

use of com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage in project pgadapter by GoogleCloudPlatform.

the class ProtocolTest method testParseMessageGsqlException.

@Test
public void testParseMessageGsqlException() throws Exception {
    byte[] messageMetadata = { 'P' };
    String statementName = "some statement\0";
    String payload = "/*GSQL*/ SELECT * FROM users WHERE name = $1\0";
    byte[] parameterCount = { 0, 1 };
    byte[] parameters = intToBytes(1002);
    byte[] length = intToBytes(4 + statementName.length() + payload.length() + parameterCount.length + parameters.length);
    byte[] value = Bytes.concat(messageMetadata, length, statementName.getBytes(), payload.getBytes(), parameterCount, parameters);
    List<Integer> expectedParameterDataTypes = Arrays.asList(1002);
    String expectedSQL = "/*GSQL*/SELECT * FROM users WHERE name = $1";
    String expectedMessageName = "some statement";
    DataInputStream inputStream = new DataInputStream(new ByteArrayInputStream(value));
    ByteArrayOutputStream result = new ByteArrayOutputStream();
    DataOutputStream outputStream = new DataOutputStream(result);
    Mockito.when(connectionHandler.getSpannerConnection()).thenReturn(connection);
    Mockito.when(connectionHandler.getConnectionMetadata()).thenReturn(connectionMetadata);
    Mockito.when(connectionMetadata.getInputStream()).thenReturn(inputStream);
    Mockito.when(connectionMetadata.getOutputStream()).thenReturn(outputStream);
    WireMessage message = ControlMessage.create(connectionHandler);
    Assert.assertEquals(message.getClass(), ParseMessage.class);
    Assert.assertEquals(((ParseMessage) message).getName(), expectedMessageName);
    Assert.assertEquals(((ParseMessage) message).getStatement().getSql(), expectedSQL);
    Assert.assertThat(((ParseMessage) message).getStatement().getParameterDataTypes(), is(expectedParameterDataTypes));
    Mockito.when(connectionHandler.hasStatement(anyString())).thenReturn(false);
    message.send();
    Mockito.verify(connectionHandler, Mockito.times(1)).registerStatement(expectedMessageName, ((ParseMessage) message).getStatement());
    // ParseCompleteResponse
    DataInputStream outputResult = inputStreamFromOutputStream(result);
    Assert.assertEquals(outputResult.readByte(), '1');
    Assert.assertEquals(outputResult.readInt(), 4);
}
Also used : ParseMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage) ByteArrayInputStream(java.io.ByteArrayInputStream) DataOutputStream(java.io.DataOutputStream) WireMessage(com.google.cloud.spanner.pgadapter.wireprotocol.WireMessage) ArgumentMatchers.anyString(org.mockito.ArgumentMatchers.anyString) ByteArrayOutputStream(java.io.ByteArrayOutputStream) DataInputStream(java.io.DataInputStream) Test(org.junit.Test)

Example 2 with ParseMessage

use of com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage in project pgadapter by GoogleCloudPlatform.

the class ProtocolTest method testParseMessageAcceptsUntypedParameter.

@Test
public void testParseMessageAcceptsUntypedParameter() throws Exception {
    byte[] messageMetadata = { 'P' };
    String statementName = "some statement\0";
    String payload = "SELECT * FROM users WHERE name = $1 /*This is a comment*/ --this is another comment\0";
    byte[] parameterCount = { 0, 1 };
    // Unspecifed parameter type.
    byte[] parameters = intToBytes(0);
    byte[] length = intToBytes(4 + statementName.length() + payload.length() + parameterCount.length + parameters.length);
    byte[] value = Bytes.concat(messageMetadata, length, statementName.getBytes(), payload.getBytes(), parameterCount, parameters);
    int[] expectedParameterDataTypes = new int[] { 0 };
    String expectedSQL = "SELECT * FROM users WHERE name = $1";
    String expectedMessageName = "some statement";
    DataInputStream inputStream = new DataInputStream(new ByteArrayInputStream(value));
    ByteArrayOutputStream result = new ByteArrayOutputStream();
    DataOutputStream outputStream = new DataOutputStream(result);
    when(connectionHandler.getServer()).thenReturn(server);
    when(server.getOptions()).thenReturn(options);
    when(connectionHandler.getSpannerConnection()).thenReturn(connection);
    when(connectionHandler.getConnectionMetadata()).thenReturn(connectionMetadata);
    when(connectionMetadata.getInputStream()).thenReturn(inputStream);
    when(connectionMetadata.getOutputStream()).thenReturn(outputStream);
    WireMessage message = ControlMessage.create(connectionHandler);
    assertEquals(ParseMessage.class, message.getClass());
    assertEquals(expectedMessageName, ((ParseMessage) message).getName());
    assertEquals(expectedSQL, ((ParseMessage) message).getStatement().getSql());
    assertArrayEquals(expectedParameterDataTypes, ((ParseMessage) message).getStatement().getParameterDataTypes());
    when(connectionHandler.hasStatement(anyString())).thenReturn(false);
    message.send();
    verify(connectionHandler).registerStatement(expectedMessageName, ((ParseMessage) message).getStatement());
    // ParseCompleteResponse
    DataInputStream outputResult = inputStreamFromOutputStream(result);
    assertEquals('1', outputResult.readByte());
    assertEquals(4, outputResult.readInt());
}
Also used : ParseMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage) ByteArrayInputStream(java.io.ByteArrayInputStream) DataOutputStream(java.io.DataOutputStream) WireMessage(com.google.cloud.spanner.pgadapter.wireprotocol.WireMessage) ArgumentMatchers.anyString(org.mockito.ArgumentMatchers.anyString) ByteArrayOutputStream(java.io.ByteArrayOutputStream) DataInputStream(java.io.DataInputStream) Test(org.junit.Test)

Example 3 with ParseMessage

use of com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage in project pgadapter by GoogleCloudPlatform.

the class JdbcMockServerTest method testCursorSuccess.

@Test
public void testCursorSuccess() throws SQLException {
    try (Connection connection = DriverManager.getConnection(createUrl())) {
        connection.setAutoCommit(false);
        try (PreparedStatement statement = connection.prepareStatement(SELECT_FIVE_ROWS.getSql())) {
            // Fetch two rows at a time from the PG server.
            statement.setFetchSize(2);
            try (ResultSet resultSet = statement.executeQuery()) {
                int index = 0;
                while (resultSet.next()) {
                    assertEquals(++index, resultSet.getInt(1));
                }
                assertEquals(5, index);
            }
        }
        connection.commit();
    }
    // The ExecuteSql request should only be sent once to Cloud Spanner.
    assertEquals(1, mockSpanner.countRequestsOfType(ExecuteSqlRequest.class));
    ExecuteSqlRequest executeRequest = mockSpanner.getRequestsOfType(ExecuteSqlRequest.class).get(0);
    assertEquals(QueryMode.NORMAL, executeRequest.getQueryMode());
    assertEquals(SELECT_FIVE_ROWS.getSql(), executeRequest.getSql());
    // 5. COMMIT
    if (pgServer != null) {
        List<DescribeMessage> describeMessages = getWireMessagesOfType(DescribeMessage.class);
        assertEquals(1, describeMessages.size());
        DescribeMessage describeMessage = describeMessages.get(0);
        assertEquals(PreparedType.Portal, describeMessage.getType());
        List<ExecuteMessage> executeMessages = getWireMessagesOfType(ExecuteMessage.class);
        assertEquals(5, executeMessages.size());
        assertEquals("", executeMessages.get(0).getName());
        for (ExecuteMessage executeMessage : executeMessages.subList(1, executeMessages.size() - 1)) {
            assertEquals(describeMessage.getName(), executeMessage.getName());
            assertEquals(2, executeMessage.getMaxRows());
        }
        assertEquals("", executeMessages.get(executeMessages.size() - 1).getName());
        List<ParseMessage> parseMessages = getWireMessagesOfType(ParseMessage.class);
        assertEquals(3, parseMessages.size());
        assertEquals("BEGIN", parseMessages.get(0).getStatement().getSql());
        assertEquals(SELECT_FIVE_ROWS.getSql(), parseMessages.get(1).getStatement().getSql());
        assertEquals("COMMIT", parseMessages.get(2).getStatement().getSql());
    }
}
Also used : ExecuteSqlRequest(com.google.spanner.v1.ExecuteSqlRequest) ParseMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage) ExecuteMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ExecuteMessage) DescribeMessage(com.google.cloud.spanner.pgadapter.wireprotocol.DescribeMessage) Connection(java.sql.Connection) ResultSet(java.sql.ResultSet) PreparedStatement(java.sql.PreparedStatement) Test(org.junit.Test)

Example 4 with ParseMessage

use of com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage in project pgadapter by GoogleCloudPlatform.

the class JdbcMockServerTest method testRandomResults.

@Test
public void testRandomResults() throws SQLException {
    final int fetchSize = 3;
    try (Connection connection = DriverManager.getConnection(createUrl())) {
        connection.setAutoCommit(false);
        try (PreparedStatement statement = connection.prepareStatement(SELECT_RANDOM.getSql())) {
            statement.setFetchSize(fetchSize);
            try (ResultSet resultSet = statement.executeQuery()) {
                int rowCount = 0;
                while (resultSet.next()) {
                    for (int col = 0; col < resultSet.getMetaData().getColumnCount(); col++) {
                        resultSet.getObject(col + 1);
                    }
                    rowCount++;
                }
                assertEquals(RANDOM_RESULTS_ROW_COUNT, rowCount);
            }
        }
        connection.commit();
    }
    // The ExecuteSql request should only be sent once to Cloud Spanner.
    assertEquals(1, mockSpanner.countRequestsOfType(ExecuteSqlRequest.class));
    ExecuteSqlRequest executeRequest = mockSpanner.getRequestsOfType(ExecuteSqlRequest.class).get(0);
    assertEquals(QueryMode.NORMAL, executeRequest.getQueryMode());
    assertEquals(SELECT_RANDOM.getSql(), executeRequest.getSql());
    // 5. COMMIT
    if (pgServer != null) {
        List<DescribeMessage> describeMessages = getWireMessagesOfType(DescribeMessage.class);
        assertEquals(1, describeMessages.size());
        DescribeMessage describeMessage = describeMessages.get(0);
        assertEquals(PreparedType.Portal, describeMessage.getType());
        List<ExecuteMessage> executeMessages = getWireMessagesOfType(ExecuteMessage.class);
        int expectedExecuteMessageCount = RANDOM_RESULTS_ROW_COUNT / fetchSize + ((RANDOM_RESULTS_ROW_COUNT % fetchSize) > 0 ? 1 : 0) + 2;
        assertEquals(expectedExecuteMessageCount, executeMessages.size());
        assertEquals("", executeMessages.get(0).getName());
        for (ExecuteMessage executeMessage : executeMessages.subList(1, executeMessages.size() - 1)) {
            assertEquals(describeMessage.getName(), executeMessage.getName());
            assertEquals(fetchSize, executeMessage.getMaxRows());
        }
        assertEquals("", executeMessages.get(executeMessages.size() - 1).getName());
        List<ParseMessage> parseMessages = getWireMessagesOfType(ParseMessage.class);
        assertEquals(3, parseMessages.size());
        assertEquals("BEGIN", parseMessages.get(0).getStatement().getSql());
        assertEquals(SELECT_RANDOM.getSql(), parseMessages.get(1).getStatement().getSql());
        assertEquals("COMMIT", parseMessages.get(2).getStatement().getSql());
    }
}
Also used : ExecuteSqlRequest(com.google.spanner.v1.ExecuteSqlRequest) ParseMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage) ExecuteMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ExecuteMessage) DescribeMessage(com.google.cloud.spanner.pgadapter.wireprotocol.DescribeMessage) Connection(java.sql.Connection) ResultSet(java.sql.ResultSet) PreparedStatement(java.sql.PreparedStatement) Test(org.junit.Test)

Example 5 with ParseMessage

use of com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage in project pgadapter by GoogleCloudPlatform.

the class ProtocolTest method testParseMessageException.

@Test
public void testParseMessageException() throws Exception {
    byte[] messageMetadata = { 'P' };
    String statementName = "some statement\0";
    String payload = "SELECT * FROM users WHERE name = $1\0";
    byte[] parameterCount = { 0, 1 };
    byte[] parameters = intToBytes(1002);
    byte[] length = intToBytes(4 + statementName.length() + payload.length() + parameterCount.length + parameters.length);
    byte[] value = Bytes.concat(messageMetadata, length, statementName.getBytes(), payload.getBytes(), parameterCount, parameters);
    int[] expectedParameterDataTypes = new int[] { 1002 };
    String expectedSQL = "SELECT * FROM users WHERE name = $1";
    String expectedMessageName = "some statement";
    DataInputStream inputStream = new DataInputStream(new ByteArrayInputStream(value));
    ByteArrayOutputStream result = new ByteArrayOutputStream();
    DataOutputStream outputStream = new DataOutputStream(result);
    when(connectionHandler.getServer()).thenReturn(server);
    when(server.getOptions()).thenReturn(options);
    when(connectionHandler.getSpannerConnection()).thenReturn(connection);
    when(connectionHandler.getConnectionMetadata()).thenReturn(connectionMetadata);
    when(connectionMetadata.getInputStream()).thenReturn(inputStream);
    when(connectionMetadata.getOutputStream()).thenReturn(outputStream);
    WireMessage message = ControlMessage.create(connectionHandler);
    assertEquals(ParseMessage.class, message.getClass());
    assertEquals(expectedMessageName, ((ParseMessage) message).getName());
    assertEquals(expectedSQL, ((ParseMessage) message).getStatement().getSql());
    assertArrayEquals(expectedParameterDataTypes, ((ParseMessage) message).getStatement().getParameterDataTypes());
    when(connectionHandler.hasStatement(anyString())).thenReturn(false);
    message.send();
    verify(connectionHandler).registerStatement(expectedMessageName, ((ParseMessage) message).getStatement());
    // ParseCompleteResponse
    DataInputStream outputResult = inputStreamFromOutputStream(result);
    assertEquals('1', outputResult.readByte());
    assertEquals(4, outputResult.readInt());
}
Also used : ParseMessage(com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage) ByteArrayInputStream(java.io.ByteArrayInputStream) DataOutputStream(java.io.DataOutputStream) WireMessage(com.google.cloud.spanner.pgadapter.wireprotocol.WireMessage) ArgumentMatchers.anyString(org.mockito.ArgumentMatchers.anyString) ByteArrayOutputStream(java.io.ByteArrayOutputStream) DataInputStream(java.io.DataInputStream) Test(org.junit.Test)

Aggregations

ParseMessage (com.google.cloud.spanner.pgadapter.wireprotocol.ParseMessage)8 Test (org.junit.Test)8 WireMessage (com.google.cloud.spanner.pgadapter.wireprotocol.WireMessage)5 ByteArrayInputStream (java.io.ByteArrayInputStream)5 ByteArrayOutputStream (java.io.ByteArrayOutputStream)5 DataInputStream (java.io.DataInputStream)5 DataOutputStream (java.io.DataOutputStream)5 ArgumentMatchers.anyString (org.mockito.ArgumentMatchers.anyString)5 DescribeMessage (com.google.cloud.spanner.pgadapter.wireprotocol.DescribeMessage)3 ExecuteMessage (com.google.cloud.spanner.pgadapter.wireprotocol.ExecuteMessage)3 ExecuteSqlRequest (com.google.spanner.v1.ExecuteSqlRequest)3 Connection (java.sql.Connection)3 PreparedStatement (java.sql.PreparedStatement)3 ResultSet (java.sql.ResultSet)3