让Eclipse的TomcatPlugin支持Tomcat 8.x
使用tomcat插件启动项目的优势:
1.TomcatPlugin是一个免重启的开发插件,原始的Servers方式启动tomcat项目,修改xxx.ftl 或者 xxx.jsp 文件后需要重启tomcat后内容才能得到更新,而使用TomcatPlugin可以避免这种重复重启项目操作;
2.多项目同时启动时较方便。在开发环境中,可能要同时启动多个项目,而每一个平台都有一个独立的域名,使用Servers情况下,如果只使用一个8080端口启动多个项目,会有冲突。但是使用TomcatPlugin,只需要配置一下hosts文件就可以很方便的访问各个项目。
实现步骤:
1.下载eclipse tomcat 插件(略)
2.配置tomcat
tomcat插件下载完成后 Window-->Preperences 中找到tomcat配置项

3.配置server.xml
在conf/目录下找到server.xml文件,并在 Engine 标签中添加如下内容:
<Host name="www2.domain1.com" appBase="webapps" unpackWARs="true" autoDeploy="true">
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs" prefix="localhost_access_log" suffix=".txt" pattern="%h %l %u %t "%r" %s %b" />
<Context path="" reloadable="true" docBase="项目目录1\src\main\webapp" workDir="项目目录1\work" >
<Loader className="org.apache.catalina.loader.DevLoader" reloadable="true" debug="1" useSystemClassLoaderAsParent="false" />
</Context>
</Host>
<Host name="www2.domain2.com" appBase="webapps" unpackWARs="true" autoDeploy="true">
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs" prefix="localhost_access_log" suffix=".txt" pattern="%h %l %u %t "%r" %s %b" />
<Context path="" reloadable="true" docBase="项目目录2\src\main\webapp" workDir="项目目录2\work" >
<Loader className="org.apache.catalina.loader.MyDevLoader" reloadable="true" debug="1" useSystemClassLoaderAsParent="false" />
</Context>
</Host>
4.配置hosts文件
在windows/system32/drivers/etc 目录下找到hosts文件,添加如下内容:
# 127.0.0.1 localhost
# ::1 localhost
127.0.0.1 www2.domain1.com www2.domain2.com www2.domain3.com
5.生成jar包
1.新建一个项目(或者使用原有的项目),创建一个包 名称为:org.apache.catalina.loader, 再创建一个类,名称为 MyDevLoader,拷贝下面java代码部分
备注:你可以随意创建一个包名和类名,但需要与 <Loader className="org.apache.catalina.loader.MyDevLoader" reloadable="true" debug="1" useSystemClassLoaderAsParent="false" /> 中的className保持一至即可。
2、消除编译报错的地方。主要是tomcat 中的lib目录下相关的jar包没有引入进来。
3、重新打成JAR包,命名DevloaderTomcat8.jar。
4、将这个jar文件放入tomcat 中的lib目录下。
package org.apache.catalina.loader; import java.io.File;
import java.io.FileFilter;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.LineNumberReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.StringTokenizer; import javax.servlet.ServletContext;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory; import org.apache.catalina.Context;
import org.apache.catalina.Globals;
import org.apache.catalina.LifecycleException;
import org.apache.catalina.loader.DevLoader.WebClassPathEntryHandler;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler; /**
* @author caoxiaobo 备注:修改DevLoader源码后的,请生成jar包,然后放置tomcat中的lib目录下;
*/
public class MyDevLoader extends WebappLoader {
private static final String info = "org.apache.catalina.loader.MyDevLoader/1.0"; private String webClassPathFile = ".#webclasspath";
private String tomcatPluginFile = ".tomcatplugin"; WebappClassLoader loader = null; /**
* @see org.apache.catalina.Lifecycle#start()
* 如果您使用的是tomcat7,此处的方法名称为start(),如果是tomcat8,此处的方法名称为startInternal()
*/
public void startInternal() throws LifecycleException {
log("Starting MyDevLoader " + info);
// setLoaderClass(DevWebappClassLoader.class.getName()); // 如果是tomcat7,此处调用 start()方法,如果是tomcat8,此处调用startInternal()方法
// super.start(); // tomcat7
super.startInternal(); // tomcat8
loader = (WebappClassLoader) super.getClassLoader();
if (loader instanceof WebappClassLoader == false) {
logError("Unable to install WebappClassLoader !");
return;
} List<String> webClassPathEntries = readWebClassPathEntries();
StringBuffer classpath = new StringBuffer();
for (Iterator<String> it = webClassPathEntries.iterator(); it.hasNext();) {
String entry = (String) it.next();
File f = new File(entry);
if (f.exists()) {
if (f.isDirectory() && entry.endsWith("/") == false)
f = new File(entry + "/");
try {
URL url = f.toURI().toURL();
loader.addURL(url); // tomcat8
// loader.addRepository(url.toString()); // tomcat7
classpath.append(f.toString() + File.pathSeparatorChar);
log("added " + url.toString());
} catch (MalformedURLException e) {
logError(entry + " invalid (MalformedURL)");
}
} else {
logError(entry + " does not exist !");
}
}
/*
* try { devCl.loadClass("at.kase.webfaces.WebApplication");
* devCl.loadClass("at.kase.taglib.BaseTag");
* devCl.loadClass("at.kase.taglib.xhtml.XHTMLTag");
* devCl.loadClass("at.kase.common.reflect.ClassHelper");
* devCl.loadClass("javax.servlet.jsp.jstl.core.Config");
* log("ALL OKAY !"); } catch(Exception e) { logError(e.toString()); }
*/
String cp = (String) getServletContext().getAttribute(Globals.CLASS_PATH_ATTR);
StringTokenizer tokenizer = new StringTokenizer(cp, File.pathSeparatorChar + "");
while (tokenizer.hasMoreTokens()) {
String token = tokenizer.nextToken();
// only on windows
if (token.charAt(0) == '/' && token.charAt(2) == ':')
token = token.substring(1);
classpath.append(token + File.pathSeparatorChar);
}
// cp = classpath + cp;
getServletContext().setAttribute(Globals.CLASS_PATH_ATTR, classpath.toString());
log("JSPCompiler Classpath = " + classpath);
} private void log(String msg) {
System.out.println("[MyDevLoader] " + msg);
} private void logError(String msg) {
System.err.println("[MyDevLoader] Error: " + msg);
} private List<String> readWebClassPathEntries() {
List<String> rc = null; File prjDir = getProjectRootDir();
if (prjDir == null) {
return new ArrayList<String>();
}
log("projectdir=" + prjDir.getAbsolutePath()); // try loading tomcat plugin file
// DON"T LOAD TOMCAT PLUGIN FILE (DOESN't HAVE FULL PATHS ANYMORE)
rc = loadTomcatPluginFile(prjDir); if (rc == null) {
//rc = loadWebClassPathFile(prjDir);
} if (rc == null)
rc = new ArrayList<String>(); // should not happen !
return rc;
} private File getProjectRootDir() {
File rootDir = getWebappDir();
FileFilter filter = new FileFilter() {
public boolean accept(File file) {
return (file.getName().equalsIgnoreCase(webClassPathFile)
|| file.getName().equalsIgnoreCase(tomcatPluginFile));
}
};
while (rootDir != null) {
File[] files = rootDir.listFiles(filter);
if (files != null && files.length >= 1) {
return files[0].getParentFile();
}
rootDir = rootDir.getParentFile();
}
return null;
} private List<String> loadWebClassPathFile(File prjDir) {
File cpFile = new File(prjDir, webClassPathFile);
if (cpFile.exists()) {
FileReader reader = null;
try {
List<String> rc = new ArrayList<String>();
reader = new FileReader(cpFile);
LineNumberReader lr = new LineNumberReader(reader);
String line = null;
while ((line = lr.readLine()) != null) {
// convert '\' to '/'
line = line.replace('\\', '/');
rc.add(line);
}
return rc;
} catch (IOException ioEx) {
ioEx.printStackTrace();
return null;
} finally {
try {
if (reader != null)
reader.close();
} catch (Exception ignored) {
}
}
} else {
return null;
}
} private List<String> loadTomcatPluginFile(File prjDir) {
File cpFile = new File(prjDir, tomcatPluginFile);
if (!cpFile.exists()) {
return null;
}
SAXParserFactory saxParserFactory = SAXParserFactory.newInstance();
SAXParser saxParser = null;
try {
saxParser = saxParserFactory.newSAXParser();
// 仿照 Digester 类来实现xml解析
WebClassPathEntryHandler dh = new WebClassPathEntryHandler();
saxParser.parse(cpFile, dh);
String[] jars = dh.getBodyText().toString().split(";");
List<String> rc = new ArrayList<String>();
for (String path : jars) {
if (isNotBlank(path)) {
// 如果是编译后../classes 文件夹路径
if (!path.endsWith(".jar")) {
if (path.endsWith("/classes")) {
path = prjDir.getParentFile() + path;
}
}
rc.add(path);
}
}
return rc;
} catch (ParserConfigurationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SAXException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
} private ServletContext getServletContext() {
// return ((Context) getContainer()).getServletContext(); // tomcat7
return super.getContext().getServletContext(); // tomcat8
} private File getWebappDir() {
File webAppDir = new File(getServletContext().getRealPath("/"));
return webAppDir;
} private static boolean isNotBlank(String str) {
return null != str && !"".equals(str) && !"".equals(str.trim());
} /**
* 内部类,用来解析 .tomcatplugin 文件中的jar
*
* @author Administrator
*
*/
private class WebClassPathEntryHandler extends DefaultHandler { private String localTag;
private StringBuilder bodyText = new StringBuilder(); @Override
public void startElement(String uri, String localName, String qName, Attributes attributes)
throws SAXException {
if (qName.equals("webClassPathEntry")) {
localTag = "webClassPathEntry";
}
} @Override
public void characters(char[] buffer, int start, int length) throws SAXException {
if ("webClassPathEntry".equals(localTag)) {
bodyText.append(buffer, start, length);
bodyText.append(";");
} } public StringBuilder getBodyText() {
return bodyText;
} }
}
特别提醒:这个类是加载你当前项目根目录下 .#webclasspath 或.tomcatplugin 文件的内容中的jar 文件的,有些项目没有这个文件,则需要从其它项目中拷贝一份出来放入你的项目根目录下。
上面那个冗余代码比较多,下面这个示例为了更方便理解Tomcat 类的加载过程,我把它优化了一下:
package org.apache.catalina.loader; import java.io.File;
import java.io.FileFilter;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.LineNumberReader;
import java.net.URL;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory; import org.apache.catalina.LifecycleException;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler; public class DevLoader extends WebappLoader { /**
* 通过 URLClassLoader 加载类/jar 文件
*/
private static WebappClassLoader loader = null; private String webClassPathFileName = ".#webclasspath";
private String tomcatPluginFileName = ".tomcatplugin"; @Override
protected void startInternal() throws LifecycleException {
super.startInternal();
// 仿照Digester获取ClassLoader的写法(Digester是用来解析xml文件的类)
loader = (WebappClassLoader) super.getClassLoader(); // 获取conf/context.xml中Context标签配置的 docBase路径
String contextPath = this.getContext().getServletContext().getRealPath("/");
System.out.println(contextPath);
File rootDir = new File(contextPath);
// 获取项目根路径
FileFilter filter = new FileFilter() {
public boolean accept(File file) {
return (file.getName().equalsIgnoreCase(webClassPathFileName)
|| file.getName().equalsIgnoreCase(tomcatPluginFileName));
}
};
// 递归向上找父文件夹
while (rootDir != null) {
File[] files = rootDir.listFiles(filter);
if ((files != null) && (files.length >= 1)) {
rootDir = files[0].getParentFile();
break;
} else {
rootDir = rootDir.getParentFile();
}
}
File webClassPathFile = new File(rootDir, webClassPathFileName);
File tomcatPluginFile = new File(rootDir, tomcatPluginFileName);
/**
* 先加载 .#webclasspath 文件
*/
if (webClassPathFile.exists()) {
loadJars$WebClasspath(webClassPathFile);
return;
}
if (tomcatPluginFile.exists()) {
loadJars$TomcatPlugin(tomcatPluginFile, rootDir);
}
} /**
* 加载jar文件 这里是解析.#webclasspath文件并加载jar文件
*/
private void loadJars$WebClasspath(File webClassPathFile) {
FileReader reader = null;
LineNumberReader lr = null;
try {
reader = new FileReader(webClassPathFile);
lr = new LineNumberReader(reader);
String path = null;
while ((path = lr.readLine()) != null) {
if (isNotBlank(path)) {
path = path.replace('\\', '/');
File file = new File(path);
URL url = file.toURI().toURL();
loader.addURL(url);
System.out.println("[DevLoader]" + path);
}
}
} catch (IOException ioEx) {
ioEx.printStackTrace();
} catch (SecurityException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} finally {
try {
if (reader != null)
reader.close();
if (lr != null)
lr.close();
} catch (IOException e) {
e.printStackTrace();
}
}
} /**
* 加载jar文件 这里是解析.tomcatplugin文件并加载jar文件
*/
private void loadJars$TomcatPlugin(File tomcatPluginFile, File rootDir) { SAXParserFactory saxParserFactory = SAXParserFactory.newInstance();
SAXParser saxParser = null;
try {
saxParser = saxParserFactory.newSAXParser();
// 仿照 Digester 类来实现xml解析
WebClassPathEntryHandler dh = new WebClassPathEntryHandler();
saxParser.parse(tomcatPluginFile, dh);
String[] jars = dh.getBodyText().toString().split(";");
for (String path : jars) {
if (isNotBlank(path)) {
// 如果是编译后../classes 文件夹路径
if (!path.endsWith(".jar")) {
if (path.endsWith("/classes")) {
path = rootDir.getParentFile() + path;
}
}
File f = new File(path.trim());
URL url = f.toURI().toURL();
loader.addURL(url);
System.out.println("[DevLoader]" + path);
}
}
} catch (ParserConfigurationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SAXException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} private static boolean isNotBlank(String str) {
return null != str && !"".equals(str) && !"".equals(str.trim());
} /**
* 内部类,用来解析 .tomcatplugin 文件中的jar
*/
class WebClassPathEntryHandler extends DefaultHandler { private String localTag;
private StringBuilder bodyText = new StringBuilder(); @Override
public void startElement(String uri, String localName, String qName, Attributes attributes)
throws SAXException {
if (qName.equals("webClassPathEntry")) {
localTag = "webClassPathEntry";
}
} @Override
public void characters(char[] buffer, int start, int length) throws SAXException {
if ("webClassPathEntry".equals(localTag)) {
bodyText.append(buffer, start, length);
bodyText.append(";");
} } public StringBuilder getBodyText() {
return bodyText;
} } }
右键项目--> Properties --> Tomcat


至此我们已经配置完结了!
点击如下图标开始启动项目

出现如下信息表示配置成功.

让Eclipse的TomcatPlugin支持Tomcat 8.x的更多相关文章
- Mac下的eclipse 4.6的tomcat插件安装正确姿势
最新版 eclipse 4.6 (Neon) tomcat 插件的安装, 解决tomcat插件tomcatPluginV331不能使用的问题. 1.打开最新版的 eclipse 4.6 (neon), ...
- JDK、Eclipse、Myeclipse、Tomcat等各种软件的版本详解(写给对版本和兼容性问题焦头烂额的你)
这篇文章我们来探讨一下关于JDK.Eclipse.Myeclipse.Tomcat的版本问题.一.关于版本的几个概念1.32位和64位两个版本: 简言之,64位的操作系统支持识别4G以上的内存条 ...
- eclipse在server中tomcat server找不到的问题
想要在eclipse的server新建tomcat服务器然而不知道怎么回事找不到Tomcat 7.0 Server 下面的红圈是tomcat server服务器(更新后才出现) 网上找的很久,只是找到 ...
- Eclipse 调试的时候Tomcat报错启动不了
Eclipse 调试的时候Tomcat报错启动不了 1.把所有的断点删掉 2.清理工程 3.在Tomcat里面删除项目 4.删除Tomcat的配置,重新配置一下
- Eclipse安装插件支持jQuery智能提示
Eclipse安装插件支持jQuery智能提示 最近工作中用到jQuery插件,需要安装eclipse插件才能支持jQuery智能提示,在网上搜索了一下,常用的有三个插件支持jQuery的智能提示:1 ...
- 在tomcat目录下启动tomcat,可以正常访问tomcat主页,然在在eclipse中集成了tomcat却访问不了tomcat主页,却能访问发布的项目
tomcat server在eclipse中正常配置了,在eclipse建tomcat服务是在server 视图那里new server建立的,但把项目部署到tomcat后却发现tomcat主页报40 ...
- Eclipse将项目部署tomcat的webapps目录
Eclipse将项目部署tomcat的webapps目录 >>>>>>>>>>>>>>>>>& ...
- 转:Eclipse Kepler已支持Java 8
文章来自于:http://www.infoq.com/cn/news/2014/04/eclipse-kepler-support-java8 期待已久的Java 8已于2014年3月19日正式发布, ...
- eclipse运行项目,tomcat报错:Exception in thread :http-bio-8080-exec-4
eclipse运行项目,tomcat报错:Exception in thread :http-bio-8080-exec-4 转自 https://www.cnblogs.com/yby-blogs/ ...
随机推荐
- HTML中a标签的锚点
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...
- DevExpress的GridControl选择一行,不显示单元格焦点的设置
grid控件默认选择一行时,focused的cell并不是蓝色的,而是白色的 要想实现一次选择一行全都是蓝色的只要改一个属性就可以了 this.gridView1.OptionsSelection.E ...
- JNI_Z_08_创建Java对象
1.步骤 : (1).获取 jclass (2).获取 构造函数的 method id (方法的名称始终为"<init>") (3).创建Java对象的两种方式: (3 ...
- 使用springmvc报错Required int parameter 'age' is not present
仔细检查jsp代码 <a href="springmvc/testRequestParam?username=atguigu$age=11">Test RequestP ...
- chrome浏览器经常无响应
chrome浏览器(v68)安装一个fiddler证书导入后点击关闭,会出现无响应 有时候动不动会无响应,今天百度了一下,发现真正的"罪魁祸首"是搜狗输入法,升级一下就好了 万恶的 ...
- sql server数据库课程设计分析
课题:能源管理收费系统 系统功能的基本要求: (1)用户基本信息的录入:包括用户的单位.部门.姓名.联系电话.住址 : (2)用户水.电.气数据的录入(每个月的数据的录入): (3)水.电.气价格的管 ...
- spring容器和上下文的理解
spring容器和上下文的理解 spring框架现在使用的很多,这说明有其独特之处----依赖注入,很简单的四个字,在我们需要对象的时候,spring就可以给我们提供所需要的对象,对象的创建.销毁.管 ...
- Ceph与OpenStack整合(仅为云主机提供云盘功能)
1. Ceph与OpenStack整合(仅为云主机提供云盘功能) 创建: linhaifeng,最新修改: 大约1分钟以前 ceph ceph osd pool create volumes 128 ...
- 由PostgreSQL的区域与字符集说起(转)
转自:http://blog.chinaunix.net/uid-354915-id-3502551.html 由PostgreSQL的区域与字符集说起 一.PostgreSQL的区域区域属性有以下几 ...
- js 扩展实例
//扩展实例1 字符串中首字符转大写 var test=' this is '; String.prototype.mytrim=function(){ var re=/^\s+(.*?)\s+$/; ...