这个包的类主要用于spring框架的异常处理和一些核心的助手类(与框架具体部分无关的)。
这个包中主要应用到了简单工厂模式,用于判断jdk版本,根据jdk版本不同提供不同的集合类、当前方法栈信息等。我们来看看是如何判断当前用户的jdk版本的:
<!---->
package org.springframework.core;
public class JdkVersion {
public static final int JAVA_13 = 0;
public static final int JAVA_14 = 1;
public static final int JAVA_15 = 2;
private static String javaVersion;
private static int majorJavaVersion = JAVA_13;
static {
javaVersion = System.getProperty("java.version");
// should look like "1.4.1_02"
if (javaVersion.indexOf("1.4.") != -1) {
majorJavaVersion = JAVA_14;
}
else if (javaVersion.indexOf("1.5.") != -1) {
majorJavaVersion = JAVA_15;
}
// else leave as 1.3 default
}
/**
* Return the full Java version string, as returned by
* <code>System.getProperty("java.version")</code>.
*/
public static String getJavaVersion() {
return javaVersion;
}
/**
* Get the major version code. This means we can do things like
* <code>if (getMajorJavaVersion() < JAVA_14)</code>.
* @return a code comparable to the JAVA_XX codes in this class
* @see #JAVA_13
* @see #JAVA_14
* @see #JAVA_15
*/
public static int getMajorJavaVersion() {
return majorJavaVersion;
}
}
直接获取系统的java.version属性来进行jdk版本的判断。而CollectionFactory依据这个类来创建不同的集合类型,如果是jdk1.4就优先使用jdk1.4的集合框架,再次选择Commons Collections,最后才不得已就使用jdk1.3的集合框架,这里比较有趣的是判断Commons Collections的方法就是尝试Class.forName一个Commons集合框架中的对象,如果成功,当然证明classpath有commons-collections.jar包:
<!---->static {
// Check whether JDK 1.4+ collections and/or
// Commons Collections 3.x are available.
if (JdkVersion.getMajorJavaVersion() >= JdkVersion.JAVA_14) {
logger.info("JDK 1.4+ collections available");
}
try {
Class.forName(COMMONS_COLLECTIONS_CLASS_NAME);
commonsCollections3xAvailable = true;
logger.info("Commons Collections 3.x available");
}
catch (ClassNotFoundException ex) {
commonsCollections3xAvailable = false;
}
}
然后就是一系列的getXXXIfPossible()方法用以获取最优版本的集合类型,比如getLinkedHashMapIfPossible():
<!---->public static Map createLinkedMapIfPossible(int initialCapacity) {
if (JdkVersion.getMajorJavaVersion() >= JdkVersion.JAVA_14) {
logger.debug("Creating [java.util.LinkedHashMap]");
return Jdk14CollectionFactory.createLinkedHashMap(initialCapacity);
}
else if (commonsCollections3xAvailable) {
logger.debug("Creating [org.apache.commons.collections.map.LinkedMap]");
return CommonsCollectionFactory.createLinkedMap(initialCapacity);
}
else {
logger.debug("Falling back to [java.util.HashMap] for linked map");
return new HashMap(initialCapacity);
}
}
其中的Jdk14CollectionFactory
和CommonsCollectionFactory
也都是工厂类。可以看到,一个优秀的通用框架对于版本的兼容性非常重视。
这个包中另外一个需要注意的就是用于spring AOP功能实现的辅助类——ControlFlow。ControlFlow按照rod johnson的说法就是用于获取当前调用的方法栈的具体信息。ControlFlow是一个接口,拥有3个方法用于判断当前方法栈的位置:
<!---->public interface ControlFlow {
/**
查找当前方法调用是否则在某类中
* @param clazz the clazz to look for
*/
boolean under(Class clazz);
/**
* 查找当前方法调用是否则在某类的某个方法中
* according to the current stack trace.
* @param clazz the clazz to look for
* @param methodName the name of the method to look for
*/
boolean under(Class clazz, String methodName);
/**
* 当前栈帧是否包含传入的记号
* @param token the token to look for
*/
boolean underToken(String token);
}
然后根据jdk版本的不同采用不同的方式实现这个接口:Jdk14ControlFlow和Jdk13ControlFlow。这是典型的
策略模式的应用。需要注意的是,这两个具体类的是放在工厂类ControlFlowFactory中作为内部类实现的:
在这里,我们可以学到的东西就如何去判断当前方法栈的信息?jdk1.4之前只能通过对StackTrace的字符串进行分析,而jdk1.4引入了java.lang.StackTraceElement用于获取当前方法调用所处的栈帧的信息,看看spring的使用方法,相当简单:
<!---->static class Jdk14ControlFlow implements ControlFlow {
private StackTraceElement[] stack;
public Jdk14ControlFlow() {
this.stack = new Throwable().getStackTrace();
}
/**
* Searches for class name match in a StackTraceElement.
*/
public boolean under(Class clazz) {
Assert.notNull(clazz, "Class must not be null");
String className = clazz.getName();
for (int i = 0; i < stack.length; i++) {
if (this.stack[i].getClassName().equals(className)) {
return true;
}
}
return false;
}
/**
* Searches for class name match plus method name match
* in a StackTraceElement.
*/
public boolean under(Class clazz, String methodName) {
Assert.notNull(clazz, "Class must not be null");
Assert.notNull(methodName, "Method name must not be null");
String className = clazz.getName();
for (int i = 0; i < this.stack.length; i++) {
if (this.stack[i].getClassName().equals(className) &&
this.stack[i].getMethodName().equals(methodName)) {
return true;
}
}
return false;
}
/**
* Leave it up to the caller to decide what matches.
* Caller must understand stack trace format, so there's less abstraction.
*/
public boolean underToken(String token) {
if (token == null) {
return false;
}
StringWriter sw = new StringWriter();
new Throwable().printStackTrace(new PrintWriter(sw));
String stackTrace = sw.toString();
return stackTrace.indexOf(token) != -1;
}
}
获取当前栈帧的信息,对于一般的java开发者没有什么意义,对于AOP的实现和框架开发者可能有比较重要的作用,我还未研读spring的aop部分,不敢妄言,留待以后解答,如果您已经研读过这部分代码,不吝赐教。
这个包另外的一个特点就是将java的反射API演示了一遍,特别是Constant.java(用于提取某个类public static final定义的常量)和ReflectiveVisitorHelper
(反射助手类),对于学习java反射技术也有不小的帮助。
分享到:
相关推荐
6. **Spring核心工具类**:`org.springframework.core` 和 `org.springframework.util` 包提供了许多实用工具类,如反射、集合操作、日志记录等。 7. **测试支持**:Spring提供了对JUnit和其他测试框架的集成,使...
`org.springframework.jdbc.core.JdbcTemplate` 提供了简单的 SQL 执行操作,而 `org.springframework.orm.hibernate3.HibernateTemplate` 和 `org.springframework.orm.jpa.EntityManagerFactoryBean` 分别为 ...
- **org.springframework.asm-3.0.4.RELEASE.jar**:ASM是一个Java字节码操控和分析框架,被Spring用于动态代理等功能。 - **org.springframework.aspects-3.0.4.RELEASE.jar**:支持Spring AOP功能。 - **org....
Spring Framework 是一个广泛使用的开源Java应用框架,特别适用于企业级应用程序开发。它的最新版本v6.1.4为我们带来了许多新特性和改进,使得开发者能够更高效、更灵活地构建可维护的、高性能的应用程序。这个...
此外,Spring的事务管理(`org.springframework.transaction`包)是其另一大亮点,提供了声明式事务管理,使得开发者无需显式调用begin、commit或rollback,即可实现事务控制。 Spring框架5.2.8.RELEASE的源码不仅...
在Spring Boot中,我们可以利用`org.springframework.data.mongodb.core.MongoTemplate`或`org.springframework.data.mongodb.repository.ReactiveMongoRepository`与MongoDB交互。对于聚合操作,我们需要使用`Mongo...
Spring Framework 5.2.15.RELEASE由多个模块组成,包括Core Container(核心容器)、Data Access/Integration(数据访问/集成)、Web、AOP(面向切面编程)、Instruments(工具类)等。每个模块都有其特定的职责,...
1. **spring-core**: 这是Spring Framework的核心模块,包含了IoC(Inversion of Control)容器的基础组件。IoC容器负责管理对象的生命周期和依赖关系,使得开发者能够将组件间的耦合度降到最低。此外,`spring-core...
- `org.springframework`:这是Spring框架的核心模块,包含了IoC(Inversion of Control,控制反转)和AOP(Aspect Oriented Programming,面向切面编程)等核心功能。如`spring-beans`提供了Bean的创建和管理,`...
import org.springframework.jms.core.JmsTemplate; import org.springframework.stereotype.Component; @Component public class MessageProducer { @Autowired private JmsTemplate jmsTemplate; public ...
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:batch="http://www.springframework.org/schema/batch" xsi:schemaLocation=...
import org.springframework.core.type.AnnotationMetadata; public class CustomRegistrar implements ImportBeanDefinitionRegistrar { @Override public void registerBeanDefinitions(AnnotationMetadata ...
在给出的jar文件列表中,我们看到了Spring的核心组件,如`org.springframework.beans`, `org.springframework.context`, `org.springframework.orm`, `org.springframework.jdbc`等,这些都是Spring框架的重要组成...
import org.springframework.context.annotation.EnableAspectJAutoProxy; @SpringBootApplication @EnableAspectJAutoProxy public class Application { public static void main(String[] args) { ...
7. **模块化设计**:Spring Framework由多个模块组成,如Core Container、Data Access/Integration、Web等,这种模块化的结构使得源码更加清晰,易于理解和扩展。 8. **注解驱动开发**:Spring 4.2进一步加强了注解...
在分析源码的过程中,我们可以深入了解Spring如何通过IoC容器管理对象,以及AOP代理是如何工作的。源码阅读有助于理解Spring的底层设计,提升我们的编程技能。 总结来说,Spring Framework 4.2.1.RELEASE是一个强大...
DEBUG org.springframework.jdbc.core.JdbcTemplate - Setting SQL parameter value: 1, java.lang.Integer ``` 3. **自定义日志**:如果你需要更细粒度的控制,比如格式化输出或者添加额外的信息,可以自定义`...
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans ...
import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.multipart.MultipartFile; import java.io....
1. **Core Container**:包括Spring的核心模块,如Bean工厂(BeanFactory)和应用上下文(ApplicationContext)。BeanFactory负责管理对象的生命周期和依赖关系,ApplicationContext则在此基础上增加了国际化、事件...