为了防止Hadoop-client与tomcat相关依赖冲突,需要排除一些jar包
<dependency>
<groupId>org.apache.hadoop</groupId>
<artifactId>hadoop-client</artifactId>
<version>3.2.3</version>
<exclusions>
<exclusion>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
</exclusion>
<exclusion>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
</exclusion>
<exclusion>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jersey</groupId>
<artifactId>jersey-servlet</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jersey</groupId>
<artifactId>jersey-core</artifactId>
</exclusion>
</exclusions>
</dependency>
然后需要定义一个servlet类,通过<load-on-startup>标签让该servlet在tomcat启动时实例化并调用其init方法
<servlet>
<servlet-name>TaskQueueSchedule</servlet-name>
<servlet-class>edu.fjnu501.securities.rpc.TaskQueueSchedule</servlet-class>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>TaskQueueSchedule</servlet-name>
<url-pattern>/task</url-pattern>
</servlet-mapping>
然后还需要注意不能将RPC初始化置于构造方法中,因为RPC.Builder也会创建该类的实例化对象,造成死循环导致栈溢出,所以应该置于init方法中
package edu.fjnu501.securities.rpc;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.ipc.RPC;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import java.io.IOException;
public class TaskQueueSchedule extends HttpServlet implements RPCProtocol {
@Override
public void init() throws ServletException {
super.init();
RPC.Server server = null;
try {
server = new RPC.Builder(new Configuration())
.setBindAddress("localhost")
.setPort(9870)
.setProtocol(RPCProtocol.class)
.setInstance(new TaskQueueSchedule())
.build();
} catch (IOException e) {
e.printStackTrace();
}
server.start();
}
}
在部署到服务器后发现,通信地址只能为localhost,且如果在更新war包时没有将原war包文件夹删除则tomcat无法启动,需要将war包文件夹删除后重新更新war包才能正常启动tomcat