- 浏览: 842452 次
- 性别:
- 来自: 深圳
文章分类
最新评论
-
renzhengzhi:
请教一下楼主,公有云和私有云的开发,具体要做哪些工作呢?我拿到 ...
4,云的4 种模式 -
SangBillLee:
我用了solr5.5,用SolrQuery查询,没法高亮,不知 ...
solr5.x快速入门 -
lw900925:
这翻译读起来真是别扭。
solr in action翻译-第一章1.1 -
springjpa_springmvc:
spring mvc demo教程源代码下载,地址:http: ...
Spring MVC性能提升 -
h416373073:
正遇到了此问题不知如何解决, 多谢分享
solr错误
tomcat使用server.xml配置属性信息
Tomcat使用开源工具Digester来讲XML元素转换为Java对象
Digester是Apache Jakarta项目下面的开源项目
org.apache.commons.digester.Digester类是Digester库里的主类。使用它来解析XML文档。
对于该文档中的每一个元素,Digester都检查它是否需要做点事情,
只需决定Digester实例在调用parser方法之前需要做什么即可
Digester对象遇到一个XML元素的时候怎么做?很简单,你定义模式并且将模式跟一条或多条规则相关联即可。
XML的根元素有一个跟他的元素名相同的模式
<?xml version="1.0" encoding="ISO-8859-1"?>
<employee firstName="Brian" lastName="May">
<office>
<address streeName="Wellington Street" streetNumber="110"/>
</office>
</employee>
该文档的根元素师employee,该元素的模式emploee。它的office元素是<employee>的子元素。
一个子元素的模式是它的名字加上它属于的元素作为前缀。所以office元素的模式是employee/office,
而address元素的模式是:
Address元素的父元素师<office>,<office>元素的模式employee/office。因此,<address>的模式employee/office/address。
规则(rules)
一个规则定义了Digester遇到特别的模式的时候必须做的动作。一个规则用org.apache.commons.digester.Rule类。
Digester类包括零个或多个Rule对象。
在一个Digester实例中,规则及其模式被存储在接口org.apache.commons.digester.Rules定义的类型中
每一次给Digester实例添加规则,都将Rule对象添加到Rules对象。
在Rule中有两个方法:begin方法和end方法。当解析一个XML文档的时候,遇到开始元素,
Digester实例调用Rule对象的begin方法,而遇到结束元素的时候调用stop方法。
example.xml所示的文档的时候,下面是Digester对象所作的.
· 第一次遇到employee开始元素,检查是否已经有存在的规则模式employee。
如果有,Digester调用Rule对象的begin方法,从begin方法开始添加第一个模式。
· 然后检查office元素,所以Digester对象检查是否存在规则模式为employee/office。如果有,,调用Rule对象的begin方法、
· 接下来检查模式employee/office/address,如果找到了规则,则调用begin方法
· 接下来Digester遇到了address结束符,调用对应规则的end方法。
· 解析来遇到了office结束符,调用相应规则的end方法。
· 最后遇到了employee结束符,调用相应规则的end方法。
Digester预先定义了一些规则,甚至在不了解Rule类的时候都可以使用这些规则。但是,如果这些规则不足够,需要建立自己的规则
创建对象
如果想让Digester给特定的规则创建对象,可以调用它的addObjectCreate方法。
该方法有四个实现,其中两个最常用方法的签名如下:
public void addObjectCreate(java.lang.String pattern, java.lang.Class clazz)
public void addObjectCreate(java.lang.String pattern, java.lang.String className)
传递一个模式和类对象(或者是类名)给它们.
例如,你想Digester根据employee模式,创建一个Employee对象(类为ex15.pyrmont.digestertest.Employee)可以使用如下代码:
digester.addObjectCreate("employee", ex15.pyrmont.digestertest.Employee.class);
或者 digester.addObjectCreate("employee", "ex15.pyrmont.digestertest.Employee");
方法addObjectCreate的另外两个实现允许在XML文档中定义类名,而不是通过作为方法参数。
这个特性带来了强大的功能,它使得类名可以在运行时决定,下面是这两个方法的签名:
public void addObjectCreate(java.lang.String pattern, java.lang.String className, java.lang.String attributeName)
public void addObjectCreate(java.lang.String pattern, java.lang.String attributeName, java.lang.Class clazz)
在这两个实现中,attributeName参数定义了XML文档中的属性,名字有className指定。
例如,如果使用下面的代码来定义创建对象规则: digester.addObjectCreate("employee", null, "className");
其中属性名为className 然后在XML中传递类名:
<employee firstName="Brian" lastName="May" className="ex15.pyrmont.digestertest.Employee">
或者可以如下在addObjectCreate方法中定义默认的类名:
digester.addObjectCreate("employee", "ex15.pyrmont.digestertest.Employee", "className");
使用addObejectCreate方法创建的对象被压到一个内部堆栈中,并定义来peek、push以及pop方法来操作创建的对象。
设置属性
另一个重要的方法是addSetProperties,Digester对象可以通过它设置对象属性。
该方法的一个实现的签名如下:
public void addSetProperties(java.lang.String pattern)
传递一个模式给该方法,例如下面的代码:
digester.addObjectCreate("employee","ex15.pyrmont.digestertest.Employee");
digester.addSetProperties("employee");
上面的Digester实例有两个规则:创建对象,设置属性。
都是关于employee模式的。根据添加的顺序来执行这些规则。
XML文档中如下的employee元素 <employee firstName="Brian" lastName="May">
方法调用
Digester允许通过添加规则,见到相应的模式的时候就调用栈最高层中对象的方法。该方法名为addCallMethod,
它的一个实现的签名如下:
public void addCallMethod (java.lang.String pattern, java.lang.String methodName)
建立对象间的联系
Digester实例有一个栈用来临时存储对象。当调用addObjectCreate创建对象后,将对象压入堆栈中。
可以把堆栈想象成一口井,可以将对象放入到井中,而pop方法相当于取出井中最上边的元素。
当通过addObjectCreate方法创建两个对象的时候,第一个对象被放入井中,然后是第二个。
addSetNext用于建立第一个对象和第二个对象之间的关系,
它把第二个对象作为参数传递给第一个对象。
下面是addSetNext方法的签名
public void addSetNext(java.lang.String pattern, java.lang.String methodName)
参数argument定义了触发该规则的模式,methodName参数是是第一个对象要被调用的方法名。
该模式的形式如firstObject/secondObject。
例如,一个employee可以有一个office,要创建一个employee和他的office之间的关系,
首先需要使用两个addObjectCreate方法。
digester.addObjectCreate("employee", "ex15.pyrmont.digestertest.Employee");
digester.addObjectCreate("employee/office", "ex15.pyrmont.digestertest.Office");
第一个addObjectCreate方法根据employee元素创建一个Employee类实例。
第二个addObjectCreate方法根据<employee>下面的<office>创建一个Office实例。
现在对象在栈底部,Office对象在栈顶部。要建立它们之间的关系,可以使用addSetNext方法方法:
digester.addSetNext("employee/office", "addOffice");
其中addOffice是Employee类的方法,该方法必须接受一个Office对象作为参数
验证XML文档
可以使用Digester来对XML文档的结构进行验证,一个XML文档是否合法取决于由Digester定义的validating属性,
该属性的默认值为false。
方法setValidating用来用来设置是否要验证XML文档,该方法的签名如下:
public void setValidating(boolean validating)
例子
public class Employee {
private String firstName;
private String lastName;
private ArrayList offices = new ArrayList();
public Employee() {
System.out.println("Creating Employee");
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
System.out.println("Setting firstName : " + firstName);
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
System.out.println("Setting lastName : " + lastName);
this.lastName = lastName;
}
public void addOffice(Office office) {
System.out.println("Adding Office to this employee");
offices.add(office);
}
public ArrayList getOffices() {
return offices;
}
public void printName() {
System.out.println("My name is " + firstName + " " + lastName);
}
}
public final class Test01 {
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
String path = System.getProperty("user.dir") + File.separator + "etc";
File file = new File(path, "employee1.xml");
Digester digester = new Digester();
// add rules
digester.addObjectCreate("employee",
"ex15.pyrmont.digestertest.Employee");
digester.addSetProperties("employee");
digester.addCallMethod("employee", "printName");
try {
Employee employee = (Employee) digester.parse(file);
System.out.println("First name : " + employee.getFirstName());
System.out.println("Last name : " + employee.getLastName());
} catch (Exception e) {
e.printStackTrace();
}
}
}
<?xml version="1.0" encoding="ISO-8859-1"?>
<employee firstName="Brian" lastName="May">
</employee>
运行Test01类得到如下运行结果:
Creating Employee
Setting firstName : Brian
Setting lastName : May
My name is Brian May
First name : Brian
Last name : May
当调用Digester对象的parse方法的时候,它打开XML文档开始解析它。首先,Digester看到了employee的开始元素。
这样触发了关于employee模式的三个规则,第一个是创建一个对象,
所以Digester初始化一个Employee类的对象,这样需要调用Employee类的构造函数,
该构造函数打印出字符串“Creating Employee”。
第二个规则设置Employee对象的属性,该元素有两个属性:firstName和lastName。
该规则调用方法这两个属性的set方法。这两个set方法打印出如下字符串
Setting firstName : Brian
Setting lastName : May
第三个规则调用printName方法,打印出如下内容:
My name is Brian May
接下来,最后两行诗调用getFirstName和getLastName方法的结果。
First name : Brian
Last name : May
例子2
第二个例子说明了如何创建两个对象,并建立它们之间的关系。
public class Office {
private Address address;
private String description;
public Office() {
System.out.println("..Creating Office");
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
System.out.println("..Setting office description : " + description);
this.description = description;
}
public Address getAddress() {
return address;
}
public void setAddress(Address address) {
System.out.println("..Setting office address : " + address);
this.address = address;
}
}
调用父对象的方法来建立它们之间的关系
public class Address {
private String streetName;
private String streetNumber;
public Address() {
System.out.println("....Creating Address");
}
public String getStreetName() {
return streetName;
}
public void setStreetName(String streetName) {
System.out.println("....Setting streetName : " + streetName);
this.streetName = streetName;
}
public String getStreetNumber() {
return streetNumber;
}
public void setStreetNumber(String streetNumber) {
System.out.println("....Setting streetNumber : " + streetNumber);
this.streetNumber = streetNumber;
}
public String toString() {
return "...." + streetNumber + " " + streetName;
}
}
第二个Digester例子说明如何创建多个对象并建立它们之间的关系
import java.io.File;
import java.util.ArrayList;
import java.util.Iterator;
import com.sun.org.apache.commons.digester.Digester;
public class Test02 {
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
String path = System.getProperty("user.dir") + File.separator + "etc";
File file = new File(path, "employee2.xml");
Digester digester = new Digester();
// add rules
digester.addObjectCreate("employee",
"ex15.pyrmont.digestertest.Employee");
digester.addSetProperties("employee");
digester.addObjectCreate("employee/office",
"ex15.pyrmont.digestertest.Office");
digester.addSetProperties("employee/office");
digester.addSetNext("employee/office", "addOffice");
digester.addObjectCreate("employee/office/address",
"ex15.pyrmont.digestertest.Address");
digester.addSetProperties("employee/office/address");
digester.addSetNext("employee/office/address", "setAddress");
try {
Employee employee = (Employee) digester.parse(file);
ArrayList offices = employee.getOffices();
Iterator iterator = offices.iterator();
System.out
.println("-------------------------------------------------");
while (iterator.hasNext()) {
Office office = (Office) iterator.next();
Address address = office.getAddress();
System.out.println(office.getDescription());
System.out.println("Address : " + address.getStreetNumber()
+ " " + address.getStreetName());
System.out.println(" -------------------------------");
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
xml如下
<?xml version="1.0" encoding="ISO-8859-1"?>
<employee firstName="Freddie" lastName="Mercury">
<office description="Headquarters">
<address streetName="Wellington Avenue" streetNumber="223"/>
</office>
<office description="Client site">
<address streetName="Downing Street" streetNumber="10"/>
</office>
</employee>
Rule类
Rule 类有多个方法,其中两个最重要的是begin和end方法。
当Digester实例遇到一个XML元素的开始标志的使用,调用所有匹配规则的begin方法。Rule类的begin方法签名如下
public void begin(org.xml.sax.Attributes attributes) throws java.lang.Exception
当Digester实例遇到XML元素的end时候,调用所有匹配规则的end方法
public void end() throws java.lang.Exception
每次调用addObjectCreate、addCallMethod、addSetNext方法的或者该类其它的方法的时候,
都会间接的调用Digester类的addRule方法,该方法会将一个Rule对象以及它的匹配模式添加到Didgester内部的规则集合中。
addRule 方法的签名如下
public void addRule(java.lang.String pattern, Rule rule)
该方法在Digester类中的实现如下:
public void addRule(String pattern, Rule rule) {
rule.setDigester(this);
getRules().add(pattern, rule);
}
addObjectCreate方法的实现:
public void addObjectCreate(String pattern, String className) {
addRule(pattern, new ObjectCreateRule(className));
}
public void addObjectCreate(String pattern, Class clazz) {
addRule(pattern, new ObjectCreateRule(clazz));
}
都调用了addRule方法,ObjectCreateRule类是Rule类的子类
begin和end方法在ObjectCreateRule类中的实现
public void begin(Attributes attributes) throws Exception {
// Identify the name of the class to instantiate
String realClassName = className;
if (attributeName != null) {
String value = attributes.getValue(attributeName);
if (value != null) {
realClassName = value; }
}
if (digester.log.isDebugEnabled()) {
digester.log.debug("[ObjectCreateRule]{" + digester.match + "}New " + realClassName);
}
// Instantiate the new object and push it on the context stack
Class clazz = digester.getClassLoader().loadclass(realClassName);
Object instance = clazz.newInstance();
digester.push(instance);
}
public void end() throws Exception {
Object top = digester.pop();
}
在begin方法中的最后三行创建了对象并将其压到Digester类的内部堆栈中,end方法使用pop方法从堆栈中获得对象。
RuleSet的使用
另一种往Digester实例添加规则方法是调用addRuleSet方法,该方法的签名如下:
public void addRuleSet(RuleSet ruleSet)
RuleSet表示了Rule对象,该接口定义了两个方法:addRuleInstance和getNamespaceURI
public void addRuleInstance(Digester digester)
方法addRuleInstance将在当前RuleSet中定义的Rule对象添加到Digester实例中,参数就是该对象。
方法getNamespaceURI返回用于请求所有规则对象的名字空间URI,它的签名如下:
public java.lang.String getNamespaceURI()
在创建完一个Digester对象后,可以创建RuleSet对象并传递一个RuleSet对象给addRuleSet方法。
有一个基本类RuleSetBase实现了RuleSet接口,RuleSetBase是一个抽象类,
它提供了getNamespaceURI的实现,你需要做的只是提供addRuleInstances的实现即可。
public class EmployeeRuleSet extends RuleSetBase {
@Override
public void addRuleInstances(Digester digester) {
digester.addObjectCreate("employee",
"ex15.pyrmont.digestertest.Employee");
digester.addSetProperties("employee");
digester.addObjectCreate("employee/office",
"ex15.pyrmont.digestertest.Office");
digester.addSetProperties("employee/office");
digester.addSetNext("employee/office", "addOffice");
digester.addObjectCreate("employee/office/address",
"ex15.pyrmont.digestertest.Address");
digester.addSetProperties("employee/office/address");
digester.addSetNext("employee/office/address", "setAddress");
}
}
注意addRuleInstances方法在EmployeeRuleSet中的实现跟Test02添加了相同的规则
public class Test03 {
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
String path = System.getProperty("user.dir") + File.separator + "etc";
File file = new File(path, "employee2.xml");
Digester digester = new Digester();
digester.addRuleSet(new EmployeeRuleSet());
try {
Employee employee = (Employee) digester.parse(file);
ArrayList offices = employee.getOffices();
Iterator iterator = offices.iterator();
System.out.println("-------------------------------------------------");
while (iterator.hasNext()) {
Office office = (Office) iterator.next();
Address address = office.getAddress();
System.out.println(office.getDescription());
System.out.println("Address : " + address.getStreetNumber()
+ " " + address.getStreetName());
System.out.println("-------------------------------");
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
注意Test03比较短,因为它将添加规则对象的操作隐藏到了EmployeeRuleSet类中。
ContextConfig类
跟其它类型的容器不同,StandardContext必须有一个监听器,
该监听器用于配置StandardContext对象并将StandardContext的configured变量设置为true。
,StandardContext的标准监听器是org.apache.catalina.startup.ContextConfig类的实例。
不像简单的SimpleContextConfig类,ContextConfig做了很多有用的工作
例如,ContextConfig实例给StandardContext的流水线安装一个验证阀门。它还给流水线添加一个证书阀门。
更重要的是,ContextConfig实例还读并解析默认的web.xml文件,并将其中的XML元素转换为Java对象
ContextConfig为每一个Servlet元素创建了一个StandardWrapper实例
defaultConfig 方法
方法defaultConfig读取并解析默认的%CATALINA_HOME%/conf目录下面的web.xml。
private void defaultConfig() {
// Open the default web.xml file, if it exists
File file = new File(Constants.DefaultWebXml);
if (!file.isAbsolute())
file = new File(System.getProperty("catalina.base"),
Constants.DefaultWebXml);
FileInputStream stream = null;
try {
stream = new FileInputStream(file.getCanonicalPath());
stream.close();
stream = null;
} catch (FileNotFoundException e) {
log(sm.getString("contextConfig.defaultMissing"));
return;
} catch (IOException e) {
log(sm.getString("contextConfig.defaultMissing"), e);
return;
}
// Process the default web.xml file
synchronized (webDigester) {
try {
InputSource is =
new InputSource("file://" + file.getAbsolutePath());
stream = new FileInputStream(file);
is.setByteStream(stream);
webDigester.setDebug(getDebug());
if (context instanceof StandardContext)
((StandardContext) context).setReplaceWelcomeFiles(true);
webDigester.clear();
webDigester.push(context);
webDigester.parse(is);
} catch (SAXParseException e) {
log(sm.getString("contextConfig.defaultParse"), e);
log(sm.getString("contextConfig.defaultPosition",
"" + e.getLineNumber(),
"" + e.getColumnNumber()));
ok = false;
} catch (Exception e) {
log(sm.getString("contextConfig.defaultParse"), e);
ok = false;
} finally {
try {
if (stream != null) {
stream.close();
}
} catch (IOException e) {
log(sm.getString("contextConfig.defaultClose"), e);
}
}
}
}
defaultConfig方法首先传教一个File对象指向默认的web.xml。
DefaultWebXML的值可以在org.apache.catalina.startup.Constants中找到:
public static final String DefaultWebXml = "conf/web.xml";
然后方法defaultConfig处理web.xml文件。它对webDigester对象枷锁,然后解析该文件。
webDigester变量指向一个Digester对象的实例,该实例用于处理web.xml并添加规则。
applicationConfig 方法
applicationConfig方法与defaultConfig方法相似,除了处理应用程序部署文件的地方。
一个应用的部署文件在该应用目录下的WEB-INF目录下面
private void applicationConfig() {
// Open the application web.xml file, if it exists
InputStream stream = null;
ServletContext servletContext = context.getServletContext();
if (servletContext != null)
stream = servletContext.getResourceAsStream
(Constants.ApplicationWebXml);
if (stream == null) {
log(sm.getString("contextConfig.applicationMissing"));
return;
}
// Process the application web.xml file
synchronized (webDigester) {
try {
URL url =
servletContext.getResource(Constants.ApplicationWebXml);
InputSource is = new InputSource(url.toExternalForm());
is.setByteStream(stream);
webDigester.setDebug(getDebug());
if (context instanceof StandardContext) {
((StandardContext) context).setReplaceWelcomeFiles(true);
}
webDigester.clear();
webDigester.push(context);
webDigester.parse(is);
} catch (SAXParseException e) {
log(sm.getString("contextConfig.applicationParse"), e);
log(sm.getString("contextConfig.applicationPosition",
"" + e.getLineNumber(),
"" + e.getColumnNumber()));
ok = false;
} catch (Exception e) {
log(sm.getString("contextConfig.applicationParse"), e);
ok = false;
} finally {
try {
if (stream != null) {
stream.close();
}
} catch (IOException e) {
log(sm.getString("contextConfig.applicationClose"), e);
}
}
}
}
创建web Digester
在ContextConfig类中存在一个名为webDigester的Digester对象:
private static Digester webDigester = createWebDigester();
该Digester用于解析默认web.xml以及应用程序web.xml。
处理web.xml的规则在调用createWebDigester方法的时候会被添加
private static Digester createWebDigester() {
URL url = null;
Digester webDigester = new Digester();
webDigester.setValidating(true);
url = ContextConfig.class.getResource(Constants.WebDtdResourcePath_22);
webDigester.register(Constants.WebDtdPublicId_22,
url.toString());
url = ContextConfig.class.getResource(Constants.WebDtdResourcePath_23);
webDigester.register(Constants.WebDtdPublicId_23,
url.toString());
webDigester.addRuleSet(new WebRuleSet());
return (webDigester);
}
注意createWebDigester方法在webDigester中调用addRuleSet的时候传递一个WebRuleSet实例.
WebRuleSet是RuleSetBase类的一个子类
public class WebRuleSet extends RuleSetBase {
// ----------------------------------------------------- Instance Variables
/**
* The matching pattern prefix to use for recognizing our elements.
*/
protected String prefix = null;
// ------------------------------------------------------------ Constructor
/**
* Construct an instance of this <code>RuleSet</code> with the default
* matching pattern prefix.
*/
public WebRuleSet() {
this("");
}
/**
* Construct an instance of this <code>RuleSet</code> with the specified
* matching pattern prefix.
*
* @param prefix Prefix for matching pattern rules (including the
* trailing slash character)
*/
public WebRuleSet(String prefix) {
super();
this.namespaceURI = null;
this.prefix = prefix;
}
// --------------------------------------------------------- Public Methods
/**
* <p>Add the set of Rule instances defined in this RuleSet to the
* specified <code>Digester</code> instance, associating them with
* our namespace URI (if any). This method should only be called
* by a Digester instance.</p>
*
* @param digester Digester instance to which the new Rule instances
* should be added.
*/
public void addRuleInstances(Digester digester) {
digester.addRule(prefix + "web-app",
new SetPublicIdRule(digester, "setPublicId"));
digester.addCallMethod(prefix + "web-app/context-param",
"addParameter", 2);
digester.addCallParam(prefix + "web-app/context-param/param-name", 0);
digester.addCallParam(prefix + "web-app/context-param/param-value", 1);
digester.addCallMethod(prefix + "web-app/display-name",
"setDisplayName", 0);
digester.addRule(prefix + "web-app/distributable",
new SetDistributableRule(digester));
digester.addObjectCreate(prefix + "web-app/ejb-local-ref",
"org.apache.catalina.deploy.ContextLocalEjb");
digester.addSetNext(prefix + "web-app/ejb-local-ref",
"addLocalEjb",
"org.apache.catalina.deploy.ContextLocalEjb");
digester.addCallMethod(prefix + "web-app/ejb-local-ref/description",
"setDescription", 0);
digester.addCallMethod(prefix + "web-app/ejb-local-ref/ejb-link",
"setLink", 0);
digester.addCallMethod(prefix + "web-app/ejb-local-ref/ejb-ref-name",
"setName", 0);
digester.addCallMethod(prefix + "web-app/ejb-local-ref/ejb-ref-type",
"setType", 0);
digester.addCallMethod(prefix + "web-app/ejb-local-ref/local",
"setLocal", 0);
digester.addCallMethod(prefix + "web-app/ejb-local-ref/local-home",
"setHome", 0);
digester.addObjectCreate(prefix + "web-app/ejb-ref",
"org.apache.catalina.deploy.ContextEjb");
digester.addSetNext(prefix + "web-app/ejb-ref",
"addEjb",
"org.apache.catalina.deploy.ContextEjb");
digester.addCallMethod(prefix + "web-app/ejb-ref/description",
"setDescription", 0);
digester.addCallMethod(prefix + "web-app/ejb-ref/ejb-link",
"setLink", 0);
digester.addCallMethod(prefix + "web-app/ejb-ref/ejb-ref-name",
"setName", 0);
digester.addCallMethod(prefix + "web-app/ejb-ref/ejb-ref-type",
"setType", 0);
digester.addCallMethod(prefix + "web-app/ejb-ref/home",
"setHome", 0);
digester.addCallMethod(prefix + "web-app/ejb-ref/remote",
"setRemote", 0);
digester.addObjectCreate(prefix + "web-app/env-entry",
"org.apache.catalina.deploy.ContextEnvironment");
digester.addSetNext(prefix + "web-app/env-entry",
"addEnvironment",
"org.apache.catalina.deploy.ContextEnvironment");
digester.addCallMethod(prefix + "web-app/env-entry/description",
"setDescription", 0);
digester.addCallMethod(prefix + "web-app/env-entry/env-entry-name",
"setName", 0);
digester.addCallMethod(prefix + "web-app/env-entry/env-entry-type",
"setType", 0);
digester.addCallMethod(prefix + "web-app/env-entry/env-entry-value",
"setValue", 0);
digester.addObjectCreate(prefix + "web-app/error-page",
"org.apache.catalina.deploy.ErrorPage");
digester.addSetNext(prefix + "web-app/error-page",
"addErrorPage",
"org.apache.catalina.deploy.ErrorPage");
digester.addCallMethod(prefix + "web-app/error-page/error-code",
"setErrorCode", 0);
digester.addCallMethod(prefix + "web-app/error-page/exception-type",
"setExceptionType", 0);
digester.addCallMethod(prefix + "web-app/error-page/location",
"setLocation", 0);
digester.addObjectCreate(prefix + "web-app/filter",
"org.apache.catalina.deploy.FilterDef");
digester.addSetNext(prefix + "web-app/filter",
"addFilterDef",
"org.apache.catalina.deploy.FilterDef");
digester.addCallMethod(prefix + "web-app/filter/description",
"setDescription", 0);
digester.addCallMethod(prefix + "web-app/filter/display-name",
"setDisplayName", 0);
digester.addCallMethod(prefix + "web-app/filter/filter-class",
"setFilterClass", 0);
digester.addCallMethod(prefix + "web-app/filter/filter-name",
"setFilterName", 0);
digester.addCallMethod(prefix + "web-app/filter/large-icon",
"setLargeIcon", 0);
digester.addCallMethod(prefix + "web-app/filter/small-icon",
"setSmallIcon", 0);
digester.addCallMethod(prefix + "web-app/filter/init-param",
"addInitParameter", 2);
digester.addCallParam(prefix + "web-app/filter/init-param/param-name",
0);
digester.addCallParam(prefix + "web-app/filter/init-param/param-value",
1);
digester.addObjectCreate(prefix + "web-app/filter-mapping",
"org.apache.catalina.deploy.FilterMap");
digester.addSetNext(prefix + "web-app/filter-mapping",
"addFilterMap",
"org.apache.catalina.deploy.FilterMap");
digester.addCallMethod(prefix + "web-app/filter-mapping/filter-name",
"setFilterName", 0);
digester.addCallMethod(prefix + "web-app/filter-mapping/servlet-name",
"setServletName", 0);
digester.addCallMethod(prefix + "web-app/filter-mapping/url-pattern",
"setURLPattern", 0);
digester.addCallMethod(prefix + "web-app/listener/listener-class",
"addApplicationListener", 0);
digester.addObjectCreate(prefix + "web-app/login-config",
"org.apache.catalina.deploy.LoginConfig");
digester.addSetNext(prefix + "web-app/login-config",
"setLoginConfig",
"org.apache.catalina.deploy.LoginConfig");
digester.addCallMethod(prefix + "web-app/login-config/auth-method",
"setAuthMethod", 0);
digester.addCallMethod(prefix + "web-app/login-config/realm-name",
"setRealmName", 0);
digester.addCallMethod(prefix + "web-app/login-config/form-login-config/form-error-page",
"setErrorPage", 0);
digester.addCallMethod(prefix + "web-app/login-config/form-login-config/form-login-page",
"setLoginPage", 0);
digester.addCallMethod(prefix + "web-app/mime-mapping",
"addMimeMapping", 2);
digester.addCallParam(prefix + "web-app/mime-mapping/extension", 0);
digester.addCallParam(prefix + "web-app/mime-mapping/mime-type", 1);
digester.addCallMethod(prefix + "web-app/resource-env-ref",
"addResourceEnvRef", 2);
digester.addCallParam(prefix + "web-app/resource-env-ref/resource-env-ref-name", 0);
digester.addCallParam(prefix + "web-app/resource-env-ref/resource-env-ref-type", 1);
digester.addObjectCreate(prefix + "web-app/resource-ref",
"org.apache.catalina.deploy.ContextResource");
digester.addSetNext(prefix + "web-app/resource-ref",
"addResource",
"org.apache.catalina.deploy.ContextResource");
digester.addCallMethod(prefix + "web-app/resource-ref/description",
"setDescription", 0);
digester.addCallMethod(prefix + "web-app/resource-ref/res-auth",
"setAuth", 0);
digester.addCallMethod(prefix + "web-app/resource-ref/res-ref-name",
"setName", 0);
digester.addCallMethod(prefix + "web-app/resource-ref/res-sharing-scope",
"setScope", 0);
digester.addCallMethod(prefix + "web-app/resource-ref/res-type",
"setType", 0);
digester.addObjectCreate(prefix + "web-app/security-constraint",
"org.apache.catalina.deploy.SecurityConstraint");
digester.addSetNext(prefix + "web-app/security-constraint",
"addConstraint",
"org.apache.catalina.deploy.SecurityConstraint");
digester.addRule(prefix + "web-app/security-constraint/auth-constraint",
new SetAuthConstraintRule(digester));
digester.addCallMethod(prefix + "web-app/security-constraint/auth-constraint/role-name",
"addAuthRole", 0);
digester.addCallMethod(prefix + "web-app/security-constraint/display-name",
"setDisplayName", 0);
digester.addCallMethod(prefix + "web-app/security-constraint/user-data-constraint/transport-guarantee",
"setUserConstraint", 0);
digester.addObjectCreate(prefix + "web-app/security-constraint/web-resource-collection",
"org.apache.catalina.deploy.SecurityCollection");
digester.addSetNext(prefix + "web-app/security-constraint/web-resource-collection",
"addCollection",
"org.apache.catalina.deploy.SecurityCollection");
digester.addCallMethod(prefix + "web-app/security-constraint/web-resource-collection/http-method",
"addMethod", 0);
digester.addCallMethod(prefix + "web-app/security-constraint/web-resource-collection/url-pattern",
"addPattern", 0);
digester.addCallMethod(prefix + "web-app/security-constraint/web-resource-collection/web-resource-name",
"setName", 0);
digester.addCallMethod(prefix + "web-app/security-role/role-name",
"addSecurityRole", 0);
digester.addRule(prefix + "web-app/servlet",
new WrapperCreateRule(digester));
digester.addSetNext(prefix + "web-app/servlet",
"addChild",
"org.apache.catalina.Container");
digester.addCallMethod(prefix + "web-app/servlet/init-param",
"addInitParameter", 2);
digester.addCallParam(prefix + "web-app/servlet/init-param/param-name",
0);
digester.addCallParam(prefix + "web-app/servlet/init-param/param-value",
1);
digester.addCallMethod(prefix + "web-app/servlet/jsp-file",
"setJspFile", 0);
digester.addCallMethod(prefix + "web-app/servlet/load-on-startup",
"setLoadOnStartupString", 0);
digester.addCallMethod(prefix + "web-app/servlet/run-as/role-name",
"setRunAs", 0);
digester.addCallMethod(prefix + "web-app/servlet/security-role-ref",
"addSecurityReference", 2);
digester.addCallParam(prefix + "web-app/servlet/security-role-ref/role-link", 1);
digester.addCallParam(prefix + "web-app/servlet/security-role-ref/role-name", 0);
digester.addCallMethod(prefix + "web-app/servlet/servlet-class",
"setServletClass", 0);
digester.addCallMethod(prefix + "web-app/servlet/servlet-name",
"setName", 0);
digester.addCallMethod(prefix + "web-app/servlet-mapping",
"addServletMapping", 2);
digester.addCallParam(prefix + "web-app/servlet-mapping/servlet-name", 1);
digester.addCallParam(prefix + "web-app/servlet-mapping/url-pattern", 0);
digester.addCallMethod(prefix + "web-app/session-config/session-timeout",
"setSessionTimeout", 1,
new Class[] { Integer.TYPE });
digester.addCallParam(prefix + "web-app/session-config/session-timeout", 0);
digester.addCallMethod(prefix + "web-app/taglib",
"addTaglib", 2);
digester.addCallParam(prefix + "web-app/taglib/taglib-location", 1);
digester.addCallParam(prefix + "web-app/taglib/taglib-uri", 0);
digester.addCallMethod(prefix + "web-app/welcome-file-list/welcome-file",
"addWelcomeFile", 0);
}
}
// ----------------------------------------------------------- Private Classes
/**
* A Rule that calls the <code>setAuthConstraint(true)</code> method of
* the top item on the stack, which must be of type
* <code>org.apache.catalina.deploy.SecurityConstraint</code>.
*/
final class SetAuthConstraintRule extends Rule {
public SetAuthConstraintRule(Digester digester) {
super(digester);
}
public void begin(Attributes attributes) throws Exception {
SecurityConstraint securityConstraint =
(SecurityConstraint) digester.peek();
securityConstraint.setAuthConstraint(true);
if (digester.getDebug() > 0)
digester.log("Calling SecurityConstraint.setAuthConstraint(true)");
}
}
/**
* Class that calls <code>setDistributable(true)</code> for the top object
* on the stack, which must be a <code>org.apache.catalina.Context</code>.
*/
final class SetDistributableRule extends Rule {
public SetDistributableRule(Digester digester) {
super(digester);
}
public void begin(Attributes attributes) throws Exception {
Context context = (Context) digester.peek();
context.setDistributable(true);
if (digester.getDebug() > 0)
digester.log(context.getClass().getName() +
".setDistributable( true)");
}
}
/**
* Class that calls a property setter for the top object on the stack,
* passing the public ID of the entity we are currently processing.
*/
final class SetPublicIdRule extends Rule {
public SetPublicIdRule(Digester digester, String method) {
super(digester);
this.method = method;
}
private String method = null;
public void begin(Attributes attributes) throws Exception {
Context context = (Context) digester.peek(digester.getCount() - 1);
Object top = digester.peek();
Class paramClasses[] = new Class[1];
paramClasses[0] = "String".getClass();
String paramValues[] = new String[1];
paramValues[0] = digester.getPublicId();
Method m = null;
try {
m = top.getClass().getMethod(method, paramClasses);
} catch (NoSuchMethodException e) {
digester.log("Can't find method " + method + " in " + top +
" CLASS " + top.getClass());
return;
}
m.invoke(top, paramValues);
if (digester.getDebug() >= 1)
digester.log("" + top.getClass().getName() + "." + method +
"(" + paramValues[0] + ")");
}
}
/**
* A Rule that calls the factory method on the specified Context to
* create the object that is to be added to the stack.
*/
final class WrapperCreateRule extends Rule {
public WrapperCreateRule(Digester digester) {
super(digester);
}
public void begin(Attributes attributes) throws Exception {
Context context =
(Context) digester.peek(digester.getCount() - 1);
Wrapper wrapper = context.createWrapper();
digester.push(wrapper);
if (digester.getDebug() > 0)
digester.log("new " + wrapper.getClass().getName());
}
public void end() throws Exception {
Wrapper wrapper = (Wrapper) digester.pop();
if (digester.getDebug() > 0)
digester.log("pop " + wrapper.getClass().getName());
}
}
Tomcat使用的是不同的配置,简单的配置配置使用server.xml文件通过Digester对象将XML元素转换为Java对象。
另外,一个web.xml文档被用于配置servlet/JSP应用。Tomcat必须能够解析web.xml文档并基于XML文档配置上下问对象,
Digester优雅的解决了这个问题。
发表评论
-
21,tomcat关闭钩子
2012-11-22 20:35 6646在很多环境下,在关闭应用程序的时候需要做一些清理工作。问题在于 ... -
19tomcat的服务器和服务
2012-11-20 20:10 1076Server服务器 Server接口表示整个Catalina ... -
18,tomcat的主机(host)和引擎
2012-11-16 09:13 2350如果需要在一个Tomcat部署中部署多个上下文,需要使用一个主 ... -
附,listener、 filter、servlet 加载顺序及其详解
2012-11-15 09:10 985一、 1、启动一个WEB项 ... -
17,tomcat中StandardContext
2012-11-15 08:59 5043一个上下文容器(Context)代表一个web应用,每一个上下 ... -
16,tomcat中StandardWrapper实现
2012-11-14 18:28 3889Wrapper接口在Catalina中的标准实现Standar ... -
15,tomcat安全
2012-11-14 09:02 1201有些web应用程序的内容是有限制的,只允许有权限的用户在提供正 ... -
14,tomcat session管理
2012-11-14 09:01 1104Catalina通过一个叫管理器的组建来完成Session的管 ... -
13.tomcat加载器
2012-11-13 13:21 1375库(repository)和源(res ... -
12,tomcat日志处理
2012-11-13 13:15 1248日志系统是一个记录信息的组件。在Catalina中,日志系统是 ... -
附:JAVA事件处理--观察者模式
2012-11-12 10:33 1001简单地说,观察者模式 ... -
11.tomcat生命周期
2012-11-12 10:26 987Catalina由多个组件组成,当Catalina启动的 ... -
10.容器
2012-11-12 10:12 1351容器是一个处理用户servlet请求并返回对象给we ... -
9.Tomcat的默认连接器
2012-11-12 08:52 1178Tomcat连接器是一个可以插入servlet容器的独立模块, ... -
8.连接器
2012-11-12 08:46 939一个可以创建更好的请 ... -
7,Facade外观模式
2012-11-08 11:28 950外观模式:为子系统中的一组接口提供了一个一致的界面,此模式定义 ... -
6,一个简单的servlet容器
2012-11-08 11:10 854总的来说,一个全功能的servlet容器会为servlet的每 ... -
5.javax.servlet.Servlet接口
2012-11-08 09:18 951javax.servlet.Servlet接口Servlet编 ... -
4,一个简单的tomcat
2012-11-07 18:10 945流程图如下 -
3.ServerSocket 与 Socket的区别
2012-11-07 16:56 11861.1 ServerSocket类创建 ...
相关推荐
- **处理事件:** Digester通过监听XML解析事件(如开始元素、结束元素)来触发规则执行。 3. **核心概念:** - **Rule:** 代表一个操作,例如创建新对象、调用对象方法、设置属性值等。每个Rule都有一个匹配...
解析这些文件的代码位于`org.apache.tomcat.util.digester`包下。 通过研究这些源代码,开发者可以了解到如何实现一个Servlet容器,如何处理网络请求,以及如何设计高效的并发处理机制等。同时,这也有助于开发者在...
1. **XML解析**:首先,`Digester`会使用`SAX`解析器来读取XML文档。SAX是一种事件驱动的解析模型,相比于DOM模型,它在处理大型XML文件时更节省内存。 2. **规则设定**:在解析XML之前,开发者需要设置一系列的`...
`Digester`是一个XML解析工具,它能够根据预定义的规则解析XML文档,将XML结构映射为Java对象。这使得Catalina能够根据XML配置文件创建和配置Servlet实例。 例如,下面的`Digester`使用示例展示了如何解析XML文档:...
1. Catalina:这是Tomcat的核心,负责管理Servlet容器,解析并执行请求。Catalina的启动过程涉及Server、Service、Engine、Host和Context等层次结构,这些元素在web.xml配置文件中定义。 2. Jasper:Jasper是Tomcat...
【标题】"Digester_jar" 是一个与Apache Commons Digester相关的...这个"Digester_jar"压缩包提供了一个便捷的途径,让开发者能够快速获取到这个库,以支持他们的XML解析需求,特别是在使用Tomcat这样的服务器环境时。
6. **配置解析**:Tomcat的配置文件如`server.xml`和`web.xml`会被解析成对象。解析过程在`org.apache.tomcat.util.digester`包下,你可以研究这些类来理解配置的处理方式。 7. **连接器(Connector)**:Tomcat...
- 源代码中的`org.apache.catalina.util.ServerInfo.java`和`org.apache.tomcat.util.digester.Digester.java`类展示了如何解析和处理这些配置文件。 5. **网络通信**: - Coyote是Tomcat的网络连接器,负责处理...
本文将深入解析Tomcat 6的启动流程,主要包括Bootstrap类、Catalina类以及XML解析器Digester的作用。 Bootstrap类是Tomcat启动的入口点,位于`org.apache.catalina.startup`包中。Bootstrap的主要任务是创建一个...
如Digester用于XML配置文件的解析,Shutdown Hook确保Tomcat的优雅关闭,Deployer负责Web应用的部署,Manager Servlet提供Web管理界面,JMX(Java Management Extensions)则实现了对Tomcat的远程监控和管理。...
在启动过程中,Tomcat首先进行必要的初始化工作,包括建立类加载器(ClassLoader)以及构建用于解析配置文件的**Digester XML解析器**。 - **建立ClassLoader** - 类加载器由`lib`目录下的多个jar包组成。 - 主要...
【Tomcat源码分析_v4 完整版1】这篇文档主要探讨了Tomcat源码中的部分核心概念,包括XML解析框架Digester的工作原理及其在Java对象映射中的应用。以下是对这些知识点的详细说明: **Java对象创建与管理:** 在...
`org.apache.tomcat.util.digester.Digester`类用于解析XML配置文件,如server.xml和context.xml,生成相应的Java对象并设置属性。 7. **JMX支持**: 通过Java Management Extensions (JMX),Tomcat提供了一种...
- `org.apache.tomcat.util.digester.Digester`:解析XML配置文件,如server.xml,将配置信息映射到对应的Java对象。 5. **线程模型**: - `org.apache.tomcat.util.net`:网络连接处理,如NioEndpoint或...
- **解析配置文件**:`digester.parse(inputSource)`解析`server.xml`,将XML元素转换为对应的Java对象,并建立这些对象之间的关系。 - **服务器初始化**:通过`getServer().setCatalina(this)`设置`Catalina`对象...
脚本解析的过程涉及到几个关键类,如Digester,它负责将XML文件中的配置转换为内部的Java对象。了解Catalina的启动脚本解析,可以让我们明白Tomcat是如何读取配置信息,以及如何根据这些配置创建和初始化各个组件的...
10. **commons-digester.jar**:用于解析XML配置文件,如struts-config.xml和tiles-defs.xml。 11. **commons-collections.jar**:提供一些集合操作的增强功能,Struts内部使用。 12. **commons-fileupload.jar**...