Запросы зависают при использовании Java-клиента Hiveserver2 Thrift

это следующий вопрос к этот вопрос где я спрашиваю, Что такое HIVESERVER 2 thrift java client API. Этот вопрос должен быть в состоянии стоять без этого фона, Если вам не нужно больше контекста.

не удалось найти документацию о том, как использовать hiverserver2 thrift api, я собрал это вместе. Лучшая ссылка, которую я мог найти, была реализация JDBC Apache.

TSocket transport = new TSocket("hive.example.com", 10002);

transport.setTimeout(999999999);
TBinaryProtocol protocol = new TBinaryProtocol(transport);
TCLIService.Client client = new TCLIService.Client(protocol);  

transport.open();
TOpenSessionReq openReq = new TOpenSessionReq();
TOpenSessionResp openResp = client.OpenSession(openReq);
TSessionHandle sessHandle = openResp.getSessionHandle();

TExecuteStatementReq execReq = new TExecuteStatementReq(sessHandle, "SHOW TABLES");
TExecuteStatementResp execResp = client.ExecuteStatement(execReq);
TOperationHandle stmtHandle = execResp.getOperationHandle();

TFetchResultsReq fetchReq = new TFetchResultsReq(stmtHandle, TFetchOrientation.FETCH_FIRST, 1);
TFetchResultsResp resultsResp = client.FetchResults(fetchReq);

TRowSet resultsSet = resultsResp.getResults();
List<TRow> resultRows = resultsSet.getRows();
for(TRow resultRow : resultRows){
    resultRow.toString();
}

TCloseOperationReq closeReq = new TCloseOperationReq();
closeReq.setOperationHandle(stmtHandle);
client.CloseOperation(closeReq);
TCloseSessionReq closeConnectionReq = new TCloseSessionReq(sessHandle);
client.CloseSession(closeConnectionReq);

transport.close();

Я запускаю этот код на Hiverserver2 экземпляр создан с

export HIVE_SERVER2_THRIFT_PORT=10002;hive --service hiveserver2

при отладке я никогда не прохожу мимо строки

TOpenSessionResp openResp = client.OpenSession(openReq);

клиент просто зависает, пока не будет достигнут тайм-аут, и сервер ничего не напишет в stdout или журналы. Используя Wireshark, я вижу, что сегмент TCP для OpenSession () отправлен и ACK'D. Как только я убиваю клиента или тайм-аут достигнут, сервер дает мне следующее:

13/03/14 11:15:33 ERROR server.TThreadPoolServer: Error occurred during processing of message.
java.lang.RuntimeException: org.apache.thrift.transport.TTransportException: java.net.SocketException: Connection reset
    at org.apache.thrift.transport.TSaslServerTransport$Factory.getTransport(TSaslServerTransport.java:219)
    at org.apache.thrift.server.TThreadPoolServer$WorkerProcess.run(TThreadPoolServer.java:189)
    at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908)
    at java.lang.Thread.run(Thread.java:662)
Caused by: org.apache.thrift.transport.TTransportException: java.net.SocketException: Connection reset
    at org.apache.thrift.transport.TIOStreamTransport.read(TIOStreamTransport.java:129)
    at org.apache.thrift.transport.TTransport.readAll(TTransport.java:84)
    at org.apache.thrift.transport.TSaslTransport.receiveSaslMessage(TSaslTransport.java:182)
    at org.apache.thrift.transport.TSaslServerTransport.handleSaslStartMessage(TSaslServerTransport.java:125)
    at org.apache.thrift.transport.TSaslTransport.open(TSaslTransport.java:253)
    at org.apache.thrift.transport.TSaslServerTransport.open(TSaslServerTransport.java:41)
    at org.apache.thrift.transport.TSaslServerTransport$Factory.getTransport(TSaslServerTransport.java:216)
    ... 4 more
Caused by: java.net.SocketException: Connection reset
    at java.net.SocketInputStream.read(SocketInputStream.java:168)
    at java.io.BufferedInputStream.read1(BufferedInputStream.java:256)
    at java.io.BufferedInputStream.read(BufferedInputStream.java:317)
    at org.apache.thrift.transport.TIOStreamTransport.read(TIOStreamTransport.java:127)
    ... 10 more

мне интересно, что это та же самая ошибка, что и я получение, когда я ошибочно пытался использовать клиент hiveserver (1) против hiveserver2, что предполагает, что, насколько это касается hiverserver2, мой клиент отправляет ему мусор.

Я вижу три возможности для того, где я могу ошибаться.

1) мое использование API клиента неверно. Я видел, что в реализации JDBC происходило что-то с параметрами аутентификации и подключения, которые я не использую в своем примере кода. Я играл с этим., но я стрелял в темноте и не продвинулся дальше.

2) я получил неверный шаг настройки. Я не смог найти TCLIService в банке hive-servive-0.10.0, но я смог найти его в банке hive-servive-0.10.0.21, выпущенной Hortonworks в HDP 1.2, поэтому, возможно, копание с этим покажет проблему. Или, может быть, есть что-то, что мне нужно настроить на стороне сервера, что объясняет, почему я могу подключиться к hive с помощью ODBC, но не с моим бережливым клиентом.

3) это может быть, на данный момент невозможно написать против клиентского api hiveserver2. Это правдоподобно, основываясь на отсутствии документации и очевидном отсутствии успешных примеров в интернете, но JDBC, похоже, делает это. Я нахожу это наиболее маловероятным вариантом.

даже если вы не знаете исправления, зная, если исправление попадает под 1, 2 или 3 поможет сузить мой поиск.

1 ответов


Не уверен, что вы все еще испытываете эту проблему, но поскольку я столкнулся с той же проблемой и решил ее (возможно, обошел более точное описание), я опубликую решение здесь на случай, если оно кому-то еще нужно.

это связано с тем, что сервер бережливости ожидает аутентификации через SASL при открытии транспортного соединения. Hive Server 2 по умолчанию использует SASL-к сожалению, PHP не имеет версии TSaslClientTransport (которая используется в качестве оболочки другой объект TTransport), который обрабатывает согласование SASL при открытии транспортного соединения.

самое простое решение на данный момент-установить следующее свойство на вашем сайте-улье.в XML

<property><name>hive.server2.authentication</name><value>NOSASL</value></property>