0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019 package org.apache.hive.service.cli.thrift;
0020
0021 import java.util.Arrays;
0022 import java.util.concurrent.SynchronousQueue;
0023 import java.util.concurrent.ThreadPoolExecutor;
0024 import java.util.concurrent.TimeUnit;
0025
0026 import org.apache.hadoop.hive.conf.HiveConf;
0027 import org.apache.hadoop.hive.conf.HiveConf.ConfVars;
0028 import org.apache.hadoop.hive.shims.ShimLoader;
0029 import org.apache.hadoop.security.UserGroupInformation;
0030 import org.apache.hadoop.util.Shell;
0031 import org.apache.hive.service.auth.HiveAuthFactory;
0032 import org.apache.hive.service.cli.CLIService;
0033 import org.apache.hive.service.rpc.thrift.TCLIService;
0034 import org.apache.hive.service.rpc.thrift.TCLIService.Iface;
0035 import org.apache.hive.service.server.ThreadFactoryWithGarbageCleanup;
0036 import org.apache.thrift.TProcessor;
0037 import org.apache.thrift.protocol.TBinaryProtocol;
0038 import org.apache.thrift.protocol.TProtocolFactory;
0039 import org.apache.thrift.server.TServlet;
0040 import org.eclipse.jetty.server.AbstractConnectionFactory;
0041 import org.eclipse.jetty.server.ConnectionFactory;
0042 import org.eclipse.jetty.server.HttpConnectionFactory;
0043 import org.eclipse.jetty.server.ServerConnector;
0044 import org.eclipse.jetty.servlet.ServletContextHandler;
0045 import org.eclipse.jetty.servlet.ServletHolder;
0046 import org.eclipse.jetty.util.ssl.SslContextFactory;
0047 import org.eclipse.jetty.util.thread.ExecutorThreadPool;
0048 import org.eclipse.jetty.util.thread.ScheduledExecutorScheduler;
0049
0050
0051 public class ThriftHttpCLIService extends ThriftCLIService {
0052
0053 public ThriftHttpCLIService(CLIService cliService) {
0054 super(cliService, ThriftHttpCLIService.class.getSimpleName());
0055 }
0056
0057
0058
0059
0060
0061
0062 @Override
0063 public void run() {
0064 try {
0065
0066
0067 String threadPoolName = "HiveServer2-HttpHandler-Pool";
0068 ThreadPoolExecutor executorService = new ThreadPoolExecutor(minWorkerThreads, maxWorkerThreads,
0069 workerKeepAliveTime, TimeUnit.SECONDS, new SynchronousQueue<Runnable>(),
0070 new ThreadFactoryWithGarbageCleanup(threadPoolName));
0071 ExecutorThreadPool threadPool = new ExecutorThreadPool(executorService);
0072
0073
0074 httpServer = new org.eclipse.jetty.server.Server(threadPool);
0075
0076
0077
0078 ConnectionFactory[] connectionFactories;
0079 boolean useSsl = hiveConf.getBoolVar(ConfVars.HIVE_SERVER2_USE_SSL);
0080 String schemeName = useSsl ? "https" : "http";
0081
0082 if (useSsl) {
0083 String keyStorePath = hiveConf.getVar(ConfVars.HIVE_SERVER2_SSL_KEYSTORE_PATH).trim();
0084 String keyStorePassword = ShimLoader.getHadoopShims().getPassword(hiveConf,
0085 HiveConf.ConfVars.HIVE_SERVER2_SSL_KEYSTORE_PASSWORD.varname);
0086 if (keyStorePath.isEmpty()) {
0087 throw new IllegalArgumentException(ConfVars.HIVE_SERVER2_SSL_KEYSTORE_PATH.varname
0088 + " Not configured for SSL connection");
0089 }
0090 SslContextFactory sslContextFactory = new SslContextFactory.Server();
0091 String[] excludedProtocols = hiveConf.getVar(ConfVars.HIVE_SSL_PROTOCOL_BLACKLIST).split(",");
0092 LOG.info("HTTP Server SSL: adding excluded protocols: " + Arrays.toString(excludedProtocols));
0093 sslContextFactory.addExcludeProtocols(excludedProtocols);
0094 LOG.info("HTTP Server SSL: SslContextFactory.getExcludeProtocols = " +
0095 Arrays.toString(sslContextFactory.getExcludeProtocols()));
0096 sslContextFactory.setKeyStorePath(keyStorePath);
0097 sslContextFactory.setKeyStorePassword(keyStorePassword);
0098 connectionFactories = AbstractConnectionFactory.getFactories(
0099 sslContextFactory, new HttpConnectionFactory());
0100 } else {
0101 connectionFactories = new ConnectionFactory[] { new HttpConnectionFactory() };
0102 }
0103 ServerConnector connector = new ServerConnector(
0104 httpServer,
0105 null,
0106
0107 new ScheduledExecutorScheduler("HiveServer2-HttpHandler-JettyScheduler", true),
0108 null,
0109 -1,
0110 -1,
0111 connectionFactories);
0112
0113 connector.setPort(portNum);
0114
0115 connector.setReuseAddress(!Shell.WINDOWS);
0116 int maxIdleTime = (int) hiveConf.getTimeVar(ConfVars.HIVE_SERVER2_THRIFT_HTTP_MAX_IDLE_TIME,
0117 TimeUnit.MILLISECONDS);
0118 connector.setIdleTimeout(maxIdleTime);
0119
0120 httpServer.addConnector(connector);
0121
0122
0123 hiveAuthFactory = new HiveAuthFactory(hiveConf);
0124 TProcessor processor = new TCLIService.Processor<Iface>(this);
0125 TProtocolFactory protocolFactory = new TBinaryProtocol.Factory();
0126
0127
0128 UserGroupInformation serviceUGI = cliService.getServiceUGI();
0129
0130 UserGroupInformation httpUGI = cliService.getHttpUGI();
0131 String authType = hiveConf.getVar(ConfVars.HIVE_SERVER2_AUTHENTICATION);
0132 TServlet thriftHttpServlet = new ThriftHttpServlet(processor, protocolFactory, authType,
0133 serviceUGI, httpUGI, hiveAuthFactory);
0134
0135
0136 final ServletContextHandler context = new ServletContextHandler(
0137 ServletContextHandler.SESSIONS);
0138 context.setContextPath("/");
0139 String httpPath = getHttpPath(hiveConf
0140 .getVar(HiveConf.ConfVars.HIVE_SERVER2_THRIFT_HTTP_PATH));
0141 httpServer.setHandler(context);
0142 context.addServlet(new ServletHolder(thriftHttpServlet), httpPath);
0143
0144
0145
0146 httpServer.start();
0147
0148
0149 portNum = connector.getLocalPort();
0150 String msg = "Started " + ThriftHttpCLIService.class.getSimpleName() + " in " + schemeName
0151 + " mode on port " + portNum + " path=" + httpPath + " with " + minWorkerThreads + "..."
0152 + maxWorkerThreads + " worker threads";
0153 LOG.info(msg);
0154 httpServer.join();
0155 } catch (Throwable t) {
0156 LOG.error(
0157 "Error starting HiveServer2: could not start "
0158 + ThriftHttpCLIService.class.getSimpleName(), t);
0159 System.exit(-1);
0160 }
0161 }
0162
0163
0164
0165
0166
0167
0168
0169 private String getHttpPath(String httpPath) {
0170 if(httpPath == null || httpPath.equals("")) {
0171 httpPath = "/*";
0172 }
0173 else {
0174 if(!httpPath.startsWith("/")) {
0175 httpPath = "/" + httpPath;
0176 }
0177 if(httpPath.endsWith("/")) {
0178 httpPath = httpPath + "*";
0179 }
0180 if(!httpPath.endsWith("/*")) {
0181 httpPath = httpPath + "/*";
0182 }
0183 }
0184 return httpPath;
0185 }
0186 }