001/** 002 * 003 * Licensed to the Apache Software Foundation (ASF) under one 004 * or more contributor license agreements. See the NOTICE file 005 * distributed with this work for additional information 006 * regarding copyright ownership. The ASF licenses this file 007 * to you under the Apache License, Version 2.0 (the 008 * "License"); you may not use this file except in compliance 009 * with the License. You may obtain a copy of the License at 010 * 011 * http://www.apache.org/licenses/LICENSE-2.0 012 * 013 * Unless required by applicable law or agreed to in writing, software 014 * distributed under the License is distributed on an "AS IS" BASIS, 015 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 016 * See the License for the specific language governing permissions and 017 * limitations under the License. 018 */ 019package org.apache.hadoop.hbase.thrift; 020 021import static org.apache.hadoop.hbase.thrift.Constants.INFOPORT_OPTION; 022import java.io.IOException; 023import java.util.ArrayList; 024import java.util.List; 025import org.apache.hadoop.conf.Configuration; 026import org.apache.hadoop.hbase.HBaseTestingUtility; 027import org.apache.hadoop.hbase.thrift.ThriftMetrics.ThriftServerType; 028import org.slf4j.Logger; 029import org.slf4j.LoggerFactory; 030import org.apache.hbase.thirdparty.com.google.common.base.Joiner; 031 032public class HBaseThriftTestingUtility { 033 034 private static final Logger LOG = LoggerFactory.getLogger(HBaseThriftTestingUtility.class); 035 private Thread thriftServerThread; 036 private volatile Exception thriftServerException; 037 private ThriftServer thriftServer; 038 private int port; 039 040 public int getServerPort() { 041 return port; 042 } 043 044 /** 045 * start thrift server 046 * @param conf configuration 047 * @param type the type of thrift server 048 * @throws Exception When starting the thrift server fails. 049 */ 050 public void startThriftServer(Configuration conf, ThriftServerType type) throws Exception { 051 List<String> args = new ArrayList<>(); 052 port = HBaseTestingUtility.randomFreePort(); 053 args.add("-" + Constants.PORT_OPTION); 054 args.add(String.valueOf(port)); 055 args.add("-" + INFOPORT_OPTION); 056 int infoPort = HBaseTestingUtility.randomFreePort(); 057 args.add(String.valueOf(infoPort)); 058 059 LOG.info("Starting Thrift Server {} on port: {} ", type, port); 060 thriftServer = createThriftServer(conf, type); 061 startThriftServerThread(args.toArray(new String[args.size()])); 062 // wait up to 10s for the server to start 063 waitForThriftServer(); 064 LOG.info("Started Thrift Server {} on port {}", type, port); 065 } 066 067 private void startThriftServerThread(final String[] args) { 068 LOG.info("Starting HBase Thrift server with command line: " + Joiner.on(" ").join(args)); 069 070 thriftServerException = null; 071 thriftServerThread = new Thread(() -> { 072 try { 073 thriftServer.run(args); 074 } catch (Exception e) { 075 thriftServerException = e; 076 } 077 }); 078 thriftServerThread.setName(ThriftServer.class.getSimpleName()); 079 thriftServerThread.start(); 080 } 081 082 /** 083 * create a new thrift server 084 * @param conf configuration 085 * @param type the type of thrift server 086 * @return the instance of ThriftServer 087 */ 088 private ThriftServer createThriftServer(Configuration conf, ThriftServerType type) { 089 switch (type) { 090 case ONE: 091 return new ThriftServer(conf); 092 case TWO: 093 return new org.apache.hadoop.hbase.thrift2.ThriftServer(conf); 094 default: 095 throw new IllegalArgumentException("Unknown type: " + type); 096 } 097 } 098 099 private void waitForThriftServer() throws Exception { 100 boolean isServing = false; 101 int i = 0; 102 while (i++ < 100) { 103 if (thriftServer.tserver == null) { 104 Thread.sleep(100); 105 } else { 106 isServing = true; 107 break; 108 } 109 } 110 111 if (!isServing) { 112 if (thriftServer != null) { 113 thriftServer.stop(); 114 } 115 throw new IOException("Failed to start thrift server "); 116 } 117 } 118 119 public void stopThriftServer() throws Exception{ 120 LOG.debug("Stopping Thrift Server"); 121 thriftServer.stop(); 122 thriftServerThread.join(); 123 if (thriftServerException != null) { 124 LOG.error("HBase Thrift server threw an exception ", thriftServerException); 125 throw new Exception(thriftServerException); 126 } 127 } 128}