|
38 | 38 | import java.time.temporal.ChronoUnit; |
39 | 39 | import java.util.Arrays; |
40 | 40 | import java.util.Base64; |
| 41 | +import java.util.EnumSet; |
41 | 42 | import java.util.List; |
42 | 43 | import java.util.Random; |
43 | 44 | import java.util.concurrent.CompletableFuture; |
@@ -308,13 +309,14 @@ public static Object[][] noResponseFailureProvider() { |
308 | 309 | } |
309 | 310 |
|
310 | 311 | @Test(groups = { "integration" }, dataProvider = "testServerErrorHandlingDataProvider") |
311 | | - public void testServerErrorHandling(ClickHouseFormat format) { |
| 312 | + public void testServerErrorHandling(ClickHouseFormat format, boolean serverCompression, boolean useHttpCompression) { |
312 | 313 | ClickHouseNode server = getServer(ClickHouseProtocol.HTTP); |
313 | 314 | try (Client client = new Client.Builder() |
314 | 315 | .addEndpoint(server.getBaseUri()) |
315 | 316 | .setUsername("default") |
316 | 317 | .setPassword("") |
317 | | - .compressServerResponse(false) |
| 318 | + .compressServerResponse(serverCompression) |
| 319 | + .useHttpCompression(useHttpCompression) |
318 | 320 | .build()) { |
319 | 321 |
|
320 | 322 | QuerySettings querySettings = new QuerySettings().setFormat(format); |
@@ -344,14 +346,45 @@ public void testServerErrorHandling(ClickHouseFormat format) { |
344 | 346 | e.printStackTrace(); |
345 | 347 | Assert.fail(e.getMessage(), e); |
346 | 348 | } |
| 349 | + |
| 350 | + try (Client client = new Client.Builder() |
| 351 | + .addEndpoint(server.getBaseUri()) |
| 352 | + .setUsername("non-existing-user") |
| 353 | + .setPassword("nothing") |
| 354 | + .compressServerResponse(serverCompression) |
| 355 | + .useHttpCompression(useHttpCompression) |
| 356 | + .build()) { |
| 357 | + |
| 358 | + try (QueryResponse response = client.query("SELECT 1").get(1, TimeUnit.SECONDS)) { |
| 359 | + Assert.fail("Expected exception"); |
| 360 | + } catch (ServerException e) { |
| 361 | + e.printStackTrace(); |
| 362 | + Assert.assertEquals(e.getCode(), 516); |
| 363 | + Assert.assertTrue(e.getMessage().startsWith("Code: 516. DB::Exception: non-existing-user: Authentication failed: password is incorrect, or there is no user with such name. (AUTHENTICATION_FAILED)"), |
| 364 | + e.getMessage()); |
| 365 | + } catch (Exception e) { |
| 366 | + e.printStackTrace(); |
| 367 | + Assert.fail("Unexpected exception", e); |
| 368 | + } |
| 369 | + } |
347 | 370 | } |
348 | 371 |
|
349 | 372 | @DataProvider(name = "testServerErrorHandlingDataProvider") |
350 | | - public static Object[] testServerErrorHandlingDataProvider() { |
351 | | - return new Object[] { ClickHouseFormat.JSON, ClickHouseFormat.TabSeparated, ClickHouseFormat.RowBinary, ClickHouseFormat.TSKV, |
352 | | - ClickHouseFormat.JSONEachRow}; |
353 | | - } |
| 373 | + public static Object[][] testServerErrorHandlingDataProvider() { |
| 374 | + EnumSet<ClickHouseFormat> formats = EnumSet.of(ClickHouseFormat.CSV, ClickHouseFormat.TSV, |
| 375 | + ClickHouseFormat.JSON, ClickHouseFormat.JSONCompact); |
| 376 | + |
| 377 | + Object[][] result = new Object[formats.size() * 3][]; |
| 378 | + |
| 379 | + int i = 0; |
| 380 | + for (ClickHouseFormat format : formats) { |
| 381 | + result[i++] = new Object[]{format, false, false}; |
| 382 | + result[i++] = new Object[]{format, true, false}; |
| 383 | + result[i++] = new Object[]{format, true, true}; |
| 384 | + } |
354 | 385 |
|
| 386 | + return result; |
| 387 | + } |
355 | 388 |
|
356 | 389 | @Test(groups = { "integration" }) |
357 | 390 | public void testErrorWithSuccessfulResponse() { |
@@ -389,6 +422,61 @@ public void testErrorWithSuccessfulResponse() { |
389 | 422 | } |
390 | 423 | } |
391 | 424 |
|
| 425 | + @Test(groups = { "integration" }, dataProvider = "testServerErrorsUncompressedDataProvider") |
| 426 | + public void testServerErrorsUncompressed(int code, String message, String expectedMessage) { |
| 427 | + WireMockServer mockServer = new WireMockServer( WireMockConfiguration |
| 428 | + .options().port(9090).notifier(new ConsoleNotifier(false))); |
| 429 | + mockServer.start(); |
| 430 | + |
| 431 | + mockServer.addStubMapping(WireMock.post(WireMock.anyUrl()) |
| 432 | + .willReturn(WireMock.aResponse() |
| 433 | + .withStatus(HttpStatus.SC_OK) |
| 434 | + .withChunkedDribbleDelay(2, 200) |
| 435 | + .withHeader("X-ClickHouse-Exception-Code", String.valueOf(code)) |
| 436 | + .withHeader("X-ClickHouse-Summary", |
| 437 | + "{ \"read_bytes\": \"10\", \"read_rows\": \"1\"}") |
| 438 | + .withBody(message)) |
| 439 | + .build()); |
| 440 | + |
| 441 | + try (Client client = new Client.Builder().addEndpoint(Protocol.HTTP, "localhost", mockServer.port(), false) |
| 442 | + .setUsername("default") |
| 443 | + .setPassword("") |
| 444 | + .compressServerResponse(false) |
| 445 | + .build()) { |
| 446 | + |
| 447 | + try (QueryResponse response = client.query("SELECT 1").get(1, TimeUnit.SECONDS)) { |
| 448 | + Assert.fail("Expected exception"); |
| 449 | + } catch (ServerException e) { |
| 450 | + e.printStackTrace(); |
| 451 | + Assert.assertEquals(e.getCode(), code); |
| 452 | + Assert.assertEquals(e.getMessage(), expectedMessage); |
| 453 | + } catch (Exception e) { |
| 454 | + e.printStackTrace(); |
| 455 | + Assert.fail("Unexpected exception", e); |
| 456 | + } |
| 457 | + } finally { |
| 458 | + mockServer.stop(); |
| 459 | + } |
| 460 | + } |
| 461 | + |
| 462 | + @DataProvider(name = "testServerErrorsUncompressedDataProvider") |
| 463 | + public static Object[][] testServerErrorsUncompressedDataProvider() { |
| 464 | + return new Object[][] { |
| 465 | + { 241, "Code: 241. DB::Exception: Memory limit (for query) exceeded: would use 97.21 MiB", |
| 466 | + "Code: 241. DB::Exception: Memory limit (for query) exceeded: would use 97.21 MiB"}, |
| 467 | + {900, "Code: 900. DB::Exception: \uD83D\uDCBE Floppy disk is full", |
| 468 | + "Code: 900. DB::Exception: \uD83D\uDCBE Floppy disk is full"}, |
| 469 | + {901, "Code: 901. DB::Exception: I write, erase, rewrite\n" + |
| 470 | + "Erase again, and then\n" + |
| 471 | + "A poppy blooms\n" + |
| 472 | + " (by Katsushika Hokusai)", |
| 473 | + "Code: 901. DB::Exception: I write, erase, rewrite " + |
| 474 | + "Erase again, and then " + |
| 475 | + "A poppy blooms" + |
| 476 | + " (by Katsushika Hokusai)"} |
| 477 | + }; |
| 478 | + } |
| 479 | + |
392 | 480 | @Test(groups = { "integration" }) |
393 | 481 | public void testAdditionalHeaders() { |
394 | 482 | WireMockServer mockServer = new WireMockServer( WireMockConfiguration |
|
0 commit comments