001/** 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.rest.client; 019 020import static org.junit.Assert.assertEquals; 021import static org.junit.Assert.assertFalse; 022import static org.junit.Assert.assertNotNull; 023import static org.junit.Assert.assertNull; 024import static org.junit.Assert.assertTrue; 025 026import java.io.IOException; 027import java.util.ArrayList; 028import java.util.Collections; 029import java.util.Iterator; 030import java.util.List; 031import org.apache.hadoop.hbase.Cell; 032import org.apache.hadoop.hbase.CellUtil; 033import org.apache.hadoop.hbase.HBaseClassTestRule; 034import org.apache.hadoop.hbase.HBaseTestingUtility; 035import org.apache.hadoop.hbase.HColumnDescriptor; 036import org.apache.hadoop.hbase.HTableDescriptor; 037import org.apache.hadoop.hbase.TableName; 038import org.apache.hadoop.hbase.client.Admin; 039import org.apache.hadoop.hbase.client.Delete; 040import org.apache.hadoop.hbase.client.Get; 041import org.apache.hadoop.hbase.client.Put; 042import org.apache.hadoop.hbase.client.Result; 043import org.apache.hadoop.hbase.client.ResultScanner; 044import org.apache.hadoop.hbase.client.Scan; 045import org.apache.hadoop.hbase.client.Table; 046import org.apache.hadoop.hbase.rest.HBaseRESTTestingUtility; 047import org.apache.hadoop.hbase.rest.RESTServlet; 048import org.apache.hadoop.hbase.testclassification.MediumTests; 049import org.apache.hadoop.hbase.testclassification.RestTests; 050import org.apache.hadoop.hbase.util.Bytes; 051import org.apache.http.Header; 052import org.apache.http.message.BasicHeader; 053import org.junit.After; 054import org.junit.AfterClass; 055import org.junit.Before; 056import org.junit.BeforeClass; 057import org.junit.ClassRule; 058import org.junit.Test; 059import org.junit.experimental.categories.Category; 060 061@Category({RestTests.class, MediumTests.class}) 062public class TestRemoteTable { 063 @ClassRule 064 public static final HBaseClassTestRule CLASS_RULE = 065 HBaseClassTestRule.forClass(TestRemoteTable.class); 066 067 // Verify that invalid URL characters and arbitrary bytes are escaped when 068 // constructing REST URLs per HBASE-7621. RemoteHTable should support row keys 069 // and qualifiers containing any byte for all table operations. 070 private static final String INVALID_URL_CHARS_1 = 071 "|\"\\^{}\u0001\u0002\u0003\u0004\u0005\u0006\u0007\u0008\u0009\u000B\u000C"; 072 073 // HColumnDescriptor prevents certain characters in column names. The following 074 // are examples of characters are allowed in column names but are not valid in 075 // URLs. 076 private static final String INVALID_URL_CHARS_2 = "|^{}\u0242"; 077 078 // Besides alphanumeric these characters can also be present in table names. 079 private static final String VALID_TABLE_NAME_CHARS = "_-."; 080 081 private static final TableName TABLE = 082 TableName.valueOf("TestRemoteTable" + VALID_TABLE_NAME_CHARS); 083 084 private static final byte[] ROW_1 = Bytes.toBytes("testrow1" + INVALID_URL_CHARS_1); 085 private static final byte[] ROW_2 = Bytes.toBytes("testrow2" + INVALID_URL_CHARS_1); 086 private static final byte[] ROW_3 = Bytes.toBytes("testrow3" + INVALID_URL_CHARS_1); 087 private static final byte[] ROW_4 = Bytes.toBytes("testrow4"+ INVALID_URL_CHARS_1); 088 089 private static final byte[] COLUMN_1 = Bytes.toBytes("a" + INVALID_URL_CHARS_2); 090 private static final byte[] COLUMN_2 = Bytes.toBytes("b" + INVALID_URL_CHARS_2); 091 private static final byte[] COLUMN_3 = Bytes.toBytes("c" + INVALID_URL_CHARS_2); 092 093 private static final byte[] QUALIFIER_1 = Bytes.toBytes("1" + INVALID_URL_CHARS_1); 094 private static final byte[] QUALIFIER_2 = Bytes.toBytes("2" + INVALID_URL_CHARS_1); 095 private static final byte[] VALUE_1 = Bytes.toBytes("testvalue1"); 096 private static final byte[] VALUE_2 = Bytes.toBytes("testvalue2"); 097 098 private static final long ONE_HOUR = 60 * 60 * 1000; 099 private static final long TS_2 = System.currentTimeMillis(); 100 private static final long TS_1 = TS_2 - ONE_HOUR; 101 102 private static final HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility(); 103 private static final HBaseRESTTestingUtility REST_TEST_UTIL = 104 new HBaseRESTTestingUtility(); 105 private RemoteHTable remoteTable; 106 107 @BeforeClass 108 public static void setUpBeforeClass() throws Exception { 109 TEST_UTIL.startMiniCluster(); 110 REST_TEST_UTIL.startServletContainer(TEST_UTIL.getConfiguration()); 111 } 112 113 @Before 114 public void before() throws Exception { 115 Admin admin = TEST_UTIL.getAdmin(); 116 if (admin.tableExists(TABLE)) { 117 if (admin.isTableEnabled(TABLE)) { 118 admin.disableTable(TABLE); 119 } 120 121 admin.deleteTable(TABLE); 122 } 123 HTableDescriptor htd = new HTableDescriptor(TABLE); 124 htd.addFamily(new HColumnDescriptor(COLUMN_1).setMaxVersions(3)); 125 htd.addFamily(new HColumnDescriptor(COLUMN_2).setMaxVersions(3)); 126 htd.addFamily(new HColumnDescriptor(COLUMN_3).setMaxVersions(3)); 127 admin.createTable(htd); 128 try (Table table = TEST_UTIL.getConnection().getTable(TABLE)) { 129 Put put = new Put(ROW_1); 130 put.addColumn(COLUMN_1, QUALIFIER_1, TS_2, VALUE_1); 131 table.put(put); 132 put = new Put(ROW_2); 133 put.addColumn(COLUMN_1, QUALIFIER_1, TS_1, VALUE_1); 134 put.addColumn(COLUMN_1, QUALIFIER_1, TS_2, VALUE_2); 135 put.addColumn(COLUMN_2, QUALIFIER_2, TS_2, VALUE_2); 136 table.put(put); 137 } 138 remoteTable = new RemoteHTable( 139 new Client(new Cluster().add("localhost", 140 REST_TEST_UTIL.getServletPort())), 141 TEST_UTIL.getConfiguration(), TABLE.toBytes()); 142 } 143 144 @After 145 public void after() throws Exception { 146 remoteTable.close(); 147 } 148 149 @AfterClass 150 public static void tearDownAfterClass() throws Exception { 151 REST_TEST_UTIL.shutdownServletContainer(); 152 TEST_UTIL.shutdownMiniCluster(); 153 } 154 155 @Test 156 public void testGetTableDescriptor() throws IOException { 157 Table table = null; 158 try { 159 table = TEST_UTIL.getConnection().getTable(TABLE); 160 HTableDescriptor local = table.getTableDescriptor(); 161 assertEquals(remoteTable.getTableDescriptor(), local); 162 } finally { 163 if (null != table) table.close(); 164 } 165 } 166 167 @Test 168 public void testGet() throws IOException { 169 Get get = new Get(ROW_1); 170 Result result = remoteTable.get(get); 171 byte[] value1 = result.getValue(COLUMN_1, QUALIFIER_1); 172 byte[] value2 = result.getValue(COLUMN_2, QUALIFIER_2); 173 assertNotNull(value1); 174 assertTrue(Bytes.equals(VALUE_1, value1)); 175 assertNull(value2); 176 177 get = new Get(ROW_1); 178 get.addFamily(COLUMN_3); 179 result = remoteTable.get(get); 180 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 181 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 182 assertNull(value1); 183 assertNull(value2); 184 185 get = new Get(ROW_1); 186 get.addColumn(COLUMN_1, QUALIFIER_1); 187 get.addColumn(COLUMN_2, QUALIFIER_2); 188 result = remoteTable.get(get); 189 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 190 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 191 assertNotNull(value1); 192 assertTrue(Bytes.equals(VALUE_1, value1)); 193 assertNull(value2); 194 195 get = new Get(ROW_2); 196 result = remoteTable.get(get); 197 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 198 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 199 assertNotNull(value1); 200 assertTrue(Bytes.equals(VALUE_2, value1)); // @TS_2 201 assertNotNull(value2); 202 assertTrue(Bytes.equals(VALUE_2, value2)); 203 204 get = new Get(ROW_2); 205 get.addFamily(COLUMN_1); 206 result = remoteTable.get(get); 207 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 208 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 209 assertNotNull(value1); 210 assertTrue(Bytes.equals(VALUE_2, value1)); // @TS_2 211 assertNull(value2); 212 213 get = new Get(ROW_2); 214 get.addColumn(COLUMN_1, QUALIFIER_1); 215 get.addColumn(COLUMN_2, QUALIFIER_2); 216 result = remoteTable.get(get); 217 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 218 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 219 assertNotNull(value1); 220 assertTrue(Bytes.equals(VALUE_2, value1)); // @TS_2 221 assertNotNull(value2); 222 assertTrue(Bytes.equals(VALUE_2, value2)); 223 224 // test timestamp 225 get = new Get(ROW_2); 226 get.addFamily(COLUMN_1); 227 get.addFamily(COLUMN_2); 228 get.setTimestamp(TS_1); 229 result = remoteTable.get(get); 230 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 231 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 232 assertNotNull(value1); 233 assertTrue(Bytes.equals(VALUE_1, value1)); // @TS_1 234 assertNull(value2); 235 236 // test timerange 237 get = new Get(ROW_2); 238 get.addFamily(COLUMN_1); 239 get.addFamily(COLUMN_2); 240 get.setTimeRange(0, TS_1 + 1); 241 result = remoteTable.get(get); 242 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 243 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 244 assertNotNull(value1); 245 assertTrue(Bytes.equals(VALUE_1, value1)); // @TS_1 246 assertNull(value2); 247 248 // test maxVersions 249 get = new Get(ROW_2); 250 get.addFamily(COLUMN_1); 251 get.setMaxVersions(2); 252 result = remoteTable.get(get); 253 int count = 0; 254 for (Cell kv: result.listCells()) { 255 if (CellUtil.matchingFamily(kv, COLUMN_1) && TS_1 == kv.getTimestamp()) { 256 assertTrue(CellUtil.matchingValue(kv, VALUE_1)); // @TS_1 257 count++; 258 } 259 if (CellUtil.matchingFamily(kv, COLUMN_1) && TS_2 == kv.getTimestamp()) { 260 assertTrue(CellUtil.matchingValue(kv, VALUE_2)); // @TS_2 261 count++; 262 } 263 } 264 assertEquals(2, count); 265 } 266 267 @Test 268 public void testMultiGet() throws Exception { 269 ArrayList<Get> gets = new ArrayList<>(2); 270 gets.add(new Get(ROW_1)); 271 gets.add(new Get(ROW_2)); 272 Result[] results = remoteTable.get(gets); 273 assertNotNull(results); 274 assertEquals(2, results.length); 275 assertEquals(1, results[0].size()); 276 assertEquals(2, results[1].size()); 277 278 //Test Versions 279 gets = new ArrayList<>(2); 280 Get g = new Get(ROW_1); 281 g.setMaxVersions(3); 282 gets.add(g); 283 gets.add(new Get(ROW_2)); 284 results = remoteTable.get(gets); 285 assertNotNull(results); 286 assertEquals(2, results.length); 287 assertEquals(1, results[0].size()); 288 assertEquals(3, results[1].size()); 289 290 //404 291 gets = new ArrayList<>(1); 292 gets.add(new Get(Bytes.toBytes("RESALLYREALLYNOTTHERE"))); 293 results = remoteTable.get(gets); 294 assertNotNull(results); 295 assertEquals(0, results.length); 296 297 gets = new ArrayList<>(3); 298 gets.add(new Get(Bytes.toBytes("RESALLYREALLYNOTTHERE"))); 299 gets.add(new Get(ROW_1)); 300 gets.add(new Get(ROW_2)); 301 results = remoteTable.get(gets); 302 assertNotNull(results); 303 assertEquals(2, results.length); 304 } 305 306 @Test 307 public void testPut() throws IOException { 308 Put put = new Put(ROW_3); 309 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 310 remoteTable.put(put); 311 312 Get get = new Get(ROW_3); 313 get.addFamily(COLUMN_1); 314 Result result = remoteTable.get(get); 315 byte[] value = result.getValue(COLUMN_1, QUALIFIER_1); 316 assertNotNull(value); 317 assertTrue(Bytes.equals(VALUE_1, value)); 318 319 // multiput 320 List<Put> puts = new ArrayList<>(3); 321 put = new Put(ROW_3); 322 put.addColumn(COLUMN_2, QUALIFIER_2, VALUE_2); 323 puts.add(put); 324 put = new Put(ROW_4); 325 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 326 puts.add(put); 327 put = new Put(ROW_4); 328 put.addColumn(COLUMN_2, QUALIFIER_2, VALUE_2); 329 puts.add(put); 330 remoteTable.put(puts); 331 332 get = new Get(ROW_3); 333 get.addFamily(COLUMN_2); 334 result = remoteTable.get(get); 335 value = result.getValue(COLUMN_2, QUALIFIER_2); 336 assertNotNull(value); 337 assertTrue(Bytes.equals(VALUE_2, value)); 338 get = new Get(ROW_4); 339 result = remoteTable.get(get); 340 value = result.getValue(COLUMN_1, QUALIFIER_1); 341 assertNotNull(value); 342 assertTrue(Bytes.equals(VALUE_1, value)); 343 value = result.getValue(COLUMN_2, QUALIFIER_2); 344 assertNotNull(value); 345 assertTrue(Bytes.equals(VALUE_2, value)); 346 347 assertTrue(Bytes.equals(Bytes.toBytes("TestRemoteTable" + VALID_TABLE_NAME_CHARS), 348 remoteTable.getTableName())); 349 } 350 351 @Test 352 public void testDelete() throws IOException { 353 Put put = new Put(ROW_3); 354 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 355 put.addColumn(COLUMN_2, QUALIFIER_2, VALUE_2); 356 put.addColumn(COLUMN_3, QUALIFIER_1, VALUE_1); 357 put.addColumn(COLUMN_3, QUALIFIER_2, VALUE_2); 358 remoteTable.put(put); 359 360 Get get = new Get(ROW_3); 361 get.addFamily(COLUMN_1); 362 get.addFamily(COLUMN_2); 363 get.addFamily(COLUMN_3); 364 Result result = remoteTable.get(get); 365 byte[] value1 = result.getValue(COLUMN_1, QUALIFIER_1); 366 byte[] value2 = result.getValue(COLUMN_2, QUALIFIER_2); 367 byte[] value3 = result.getValue(COLUMN_3, QUALIFIER_1); 368 byte[] value4 = result.getValue(COLUMN_3, QUALIFIER_2); 369 assertNotNull(value1); 370 assertTrue(Bytes.equals(VALUE_1, value1)); 371 assertNotNull(value2); 372 assertTrue(Bytes.equals(VALUE_2, value2)); 373 assertNotNull(value3); 374 assertTrue(Bytes.equals(VALUE_1, value3)); 375 assertNotNull(value4); 376 assertTrue(Bytes.equals(VALUE_2, value4)); 377 378 Delete delete = new Delete(ROW_3); 379 delete.addColumn(COLUMN_2, QUALIFIER_2); 380 remoteTable.delete(delete); 381 382 get = new Get(ROW_3); 383 get.addFamily(COLUMN_1); 384 get.addFamily(COLUMN_2); 385 result = remoteTable.get(get); 386 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 387 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 388 assertNotNull(value1); 389 assertTrue(Bytes.equals(VALUE_1, value1)); 390 assertNull(value2); 391 392 delete = new Delete(ROW_3); 393 delete.setTimestamp(1L); 394 remoteTable.delete(delete); 395 396 get = new Get(ROW_3); 397 get.addFamily(COLUMN_1); 398 get.addFamily(COLUMN_2); 399 result = remoteTable.get(get); 400 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 401 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 402 assertNotNull(value1); 403 assertTrue(Bytes.equals(VALUE_1, value1)); 404 assertNull(value2); 405 406 // Delete column family from row 407 delete = new Delete(ROW_3); 408 delete.addFamily(COLUMN_3); 409 remoteTable.delete(delete); 410 411 get = new Get(ROW_3); 412 get.addFamily(COLUMN_3); 413 result = remoteTable.get(get); 414 value3 = result.getValue(COLUMN_3, QUALIFIER_1); 415 value4 = result.getValue(COLUMN_3, QUALIFIER_2); 416 assertNull(value3); 417 assertNull(value4); 418 419 delete = new Delete(ROW_3); 420 remoteTable.delete(delete); 421 422 get = new Get(ROW_3); 423 get.addFamily(COLUMN_1); 424 get.addFamily(COLUMN_2); 425 result = remoteTable.get(get); 426 value1 = result.getValue(COLUMN_1, QUALIFIER_1); 427 value2 = result.getValue(COLUMN_2, QUALIFIER_2); 428 assertNull(value1); 429 assertNull(value2); 430 } 431 432 /** 433 * Test RemoteHTable.Scanner 434 */ 435 @Test 436 public void testScanner() throws IOException { 437 List<Put> puts = new ArrayList<>(4); 438 Put put = new Put(ROW_1); 439 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 440 puts.add(put); 441 put = new Put(ROW_2); 442 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 443 puts.add(put); 444 put = new Put(ROW_3); 445 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 446 puts.add(put); 447 put = new Put(ROW_4); 448 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 449 puts.add(put); 450 remoteTable.put(puts); 451 452 ResultScanner scanner = remoteTable.getScanner(new Scan()); 453 454 Result[] results = scanner.next(1); 455 assertNotNull(results); 456 assertEquals(1, results.length); 457 assertTrue(Bytes.equals(ROW_1, results[0].getRow())); 458 459 Result result = scanner.next(); 460 assertNotNull(result); 461 assertTrue(Bytes.equals(ROW_2, result.getRow())); 462 463 results = scanner.next(2); 464 assertNotNull(results); 465 assertEquals(2, results.length); 466 assertTrue(Bytes.equals(ROW_3, results[0].getRow())); 467 assertTrue(Bytes.equals(ROW_4, results[1].getRow())); 468 469 results = scanner.next(1); 470 assertNull(results); 471 scanner.close(); 472 473 scanner = remoteTable.getScanner(COLUMN_1); 474 results = scanner.next(4); 475 assertNotNull(results); 476 assertEquals(4, results.length); 477 assertTrue(Bytes.equals(ROW_1, results[0].getRow())); 478 assertTrue(Bytes.equals(ROW_2, results[1].getRow())); 479 assertTrue(Bytes.equals(ROW_3, results[2].getRow())); 480 assertTrue(Bytes.equals(ROW_4, results[3].getRow())); 481 482 scanner.close(); 483 484 scanner = remoteTable.getScanner(COLUMN_1,QUALIFIER_1); 485 results = scanner.next(4); 486 assertNotNull(results); 487 assertEquals(4, results.length); 488 assertTrue(Bytes.equals(ROW_1, results[0].getRow())); 489 assertTrue(Bytes.equals(ROW_2, results[1].getRow())); 490 assertTrue(Bytes.equals(ROW_3, results[2].getRow())); 491 assertTrue(Bytes.equals(ROW_4, results[3].getRow())); 492 scanner.close(); 493 assertTrue(remoteTable.isAutoFlush()); 494 } 495 496 @Test 497 public void testCheckAndDelete() throws IOException { 498 Get get = new Get(ROW_1); 499 Result result = remoteTable.get(get); 500 byte[] value1 = result.getValue(COLUMN_1, QUALIFIER_1); 501 byte[] value2 = result.getValue(COLUMN_2, QUALIFIER_2); 502 assertNotNull(value1); 503 assertTrue(Bytes.equals(VALUE_1, value1)); 504 assertNull(value2); 505 assertTrue(remoteTable.exists(get)); 506 assertEquals(1, remoteTable.existsAll(Collections.singletonList(get)).length); 507 Delete delete = new Delete(ROW_1); 508 509 remoteTable.checkAndMutate(ROW_1, COLUMN_1).qualifier(QUALIFIER_1) 510 .ifEquals(VALUE_1).thenDelete(delete); 511 assertFalse(remoteTable.exists(get)); 512 513 Put put = new Put(ROW_1); 514 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 515 remoteTable.put(put); 516 517 assertTrue(remoteTable.checkAndMutate(ROW_1, COLUMN_1).qualifier(QUALIFIER_1) 518 .ifEquals(VALUE_1).thenPut(put)); 519 assertFalse(remoteTable.checkAndMutate(ROW_1, COLUMN_1).qualifier(QUALIFIER_1) 520 .ifEquals(VALUE_2).thenPut(put)); 521 } 522 523 /** 524 * Test RemoteHable.Scanner.iterator method 525 */ 526 @Test 527 public void testIteratorScaner() throws IOException { 528 List<Put> puts = new ArrayList<>(4); 529 Put put = new Put(ROW_1); 530 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 531 puts.add(put); 532 put = new Put(ROW_2); 533 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 534 puts.add(put); 535 put = new Put(ROW_3); 536 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 537 puts.add(put); 538 put = new Put(ROW_4); 539 put.addColumn(COLUMN_1, QUALIFIER_1, VALUE_1); 540 puts.add(put); 541 remoteTable.put(puts); 542 543 ResultScanner scanner = remoteTable.getScanner(new Scan()); 544 Iterator<Result> iterator = scanner.iterator(); 545 assertTrue(iterator.hasNext()); 546 int counter = 0; 547 while (iterator.hasNext()) { 548 iterator.next(); 549 counter++; 550 } 551 assertEquals(4, counter); 552 } 553 554 /** 555 * Test a some methods of class Response. 556 */ 557 @Test 558 public void testResponse(){ 559 Response response = new Response(200); 560 assertEquals(200, response.getCode()); 561 Header[] headers = new Header[2]; 562 headers[0] = new BasicHeader("header1", "value1"); 563 headers[1] = new BasicHeader("header2", "value2"); 564 response = new Response(200, headers); 565 assertEquals("value1", response.getHeader("header1")); 566 assertFalse(response.hasBody()); 567 response.setCode(404); 568 assertEquals(404, response.getCode()); 569 headers = new Header[2]; 570 headers[0] = new BasicHeader("header1", "value1.1"); 571 headers[1] = new BasicHeader("header2", "value2"); 572 response.setHeaders(headers); 573 assertEquals("value1.1", response.getHeader("header1")); 574 response.setBody(Bytes.toBytes("body")); 575 assertTrue(response.hasBody()); 576 } 577 578 /** 579 * Tests keeping a HBase scanner alive for long periods of time. Each call to next() should reset 580 * the ConnectionCache timeout for the scanner's connection. 581 * 582 * @throws Exception if starting the servlet container or disabling or truncating the table fails 583 */ 584 @Test 585 public void testLongLivedScan() throws Exception { 586 int numTrials = 6; 587 int trialPause = 1000; 588 int cleanUpInterval = 100; 589 590 // Shutdown the Rest Servlet container 591 REST_TEST_UTIL.shutdownServletContainer(); 592 593 // Set the ConnectionCache timeout to trigger halfway through the trials 594 TEST_UTIL.getConfiguration().setLong(RESTServlet.MAX_IDLETIME, (numTrials / 2) * trialPause); 595 TEST_UTIL.getConfiguration().setLong(RESTServlet.CLEANUP_INTERVAL, cleanUpInterval); 596 597 // Start the Rest Servlet container 598 REST_TEST_UTIL.startServletContainer(TEST_UTIL.getConfiguration()); 599 600 // Truncate the test table for inserting test scenarios rows keys 601 TEST_UTIL.getHBaseAdmin().disableTable(TABLE); 602 TEST_UTIL.getHBaseAdmin().truncateTable(TABLE, false); 603 604 remoteTable = new RemoteHTable( 605 new Client(new Cluster().add("localhost", REST_TEST_UTIL.getServletPort())), 606 TEST_UTIL.getConfiguration(), TABLE.toBytes()); 607 608 String row = "testrow"; 609 610 try (Table table = TEST_UTIL.getConnection().getTable(TABLE)) { 611 List<Put> puts = new ArrayList<Put>(); 612 Put put = null; 613 for (int i = 1; i <= numTrials; i++) { 614 put = new Put(Bytes.toBytes(row + i)); 615 put.addColumn(COLUMN_1, QUALIFIER_1, TS_2, Bytes.toBytes("testvalue" + i)); 616 puts.add(put); 617 } 618 table.put(puts); 619 } 620 621 Scan scan = new Scan(); 622 scan.setCaching(1); 623 scan.setBatch(1); 624 625 ResultScanner scanner = remoteTable.getScanner(scan); 626 Result result = null; 627 // get scanner and rows 628 for (int i = 1; i <= numTrials; i++) { 629 // Make sure that the Scanner doesn't throw an exception after the ConnectionCache timeout 630 result = scanner.next(); 631 assertEquals(row + i, Bytes.toString(result.getRow())); 632 Thread.sleep(trialPause); 633 } 634 } 635}