Spring 5.2.13 源码编译 环境搭建

博文目录


准备

修改 idea 配置, File - Settings - Build, Execution, Deployment - Build Tools - Gradle, 修改 Gradle user home 为指定路径, 使用 idea 构建 spring 源码过程中自行下载的Gradle和依赖等都会存放在这个目录, 不然会和cmd运行 gradles 一样都存放在C盘用户目录下的 .gradle 文件夹下

选择一个合适的Tag版本, 下载源码 GitHub Spring Framework, 这里选的是 v5.2.13.RELEASE

先修改 ‘build.gradle’ 中 repositories 的内容, 添加 阿里云 的仓库印射, 构建时下载依赖应该会快一点

		repositories {
			mavenLocal()
			maven {url 'https://maven.aliyun.com/repository/central'}
			maven {url 'https://maven.aliyun.com/repository/public'}
			maven {url 'https://maven.aliyun.com/repository/public'}
			maven {url 'https://maven.aliyun.com/repository/google'}
			maven {url 'https://maven.aliyun.com/repository/gradle-plugin'}
			maven {url 'https://maven.aliyun.com/repository/spring'}
			maven {url 'https://maven.aliyun.com/repository/spring-plugin'}
			maven {url 'https://maven.aliyun.com/repository/grails-core'}
			maven {url 'https://maven.aliyun.com/repository/apache-snapshots'}
			mavenCentral()
			maven { url "https://repo.spring.io/libs-spring-framework-build" }
		}

预编译

阅读导入到 idea 的帮助文档 import-into-idea.md

打开cmd, cd 到源码根目录, 如 C:\mrathena\develop\workspace\idea\mrathena\study>cd spring-source-5.2.13

按照帮助文件说明, 运行 gradlew :spring-oxm:compileTestJava, 稍等一会儿提示 BUILD SUCCESSFUL, 这个 git 的报错不用管
在这里插入图片描述

导入 idea

先打开一个其他工程, 然后点击 File - New - Project from Existing sources… , 选择当前源码目录下的 build.gradle 文件, 点击 OK 导入, idea 会自动开始 build, 等待其完成, 最终也是提示 BUILD SUCCESSFUL, 同样, git 的报错不用管
在这里插入图片描述

构建完成之后, 点击 File - Project Structure - Modules, 里面将会出现一个 spring 模块, 选中其中的 spring-aspects 子模块, 点击 - 号排除

点击 Gradle面板 - spring - Tasks - build - build, 把整个工程完整构建一遍, 这样会避开很多奇怪的问题

README 展示 BUILD STATUS: FAILURE, 但是无关紧要

新建测试模块

新建一个 Gradle 模块, 用于测试和debug, 在其 gradle 配置中的 dependencies 中添加 sprign-context 的引用 compile(project(":spring-context"))

dependencies {
    compile(project(":spring-context"))
    // compile(project(":spring-aspects"))
    compile 'org.slf4j:slf4j-api:1.7.30'
    compile 'org.slf4j:jcl-over-slf4j:1.7.30'
    compile 'org.slf4j:jul-to-slf4j:1.7.30'
    compile 'org.slf4j:log4j-over-slf4j:1.7.30'
    compile 'ch.qos.logback:logback-classic:1.2.3'
    // Gradle 5.0版本以下. 只编译时有效,不参与打包。代替旧版本的provided
    // compileOnly 'org.projectlombok:lombok:1.18.20'
    // Gradle 5.0及以上版本. 管理注解处理器,并将其添加到处理器类路径中
    // annotationProcessor 'org.projectlombok:lombok:1.18.20'
    testImplementation 'org.junit.jupiter:junit-jupiter-api:5.6.0'
    testRuntimeOnly 'org.junit.jupiter:junit-jupiter-engine'
}

点击 File - Settings - Build, Execution, Deployment - Build Tools - Gradle, Build and run using 和 Run tests using 两个选项都选择 IntelliJ IDEA, 这样不必每次都跑一堆任务, 即可直接运行测试代码

新建一个配置类

@Configuration
public class Application {

	@Bean
	public String string() {
		return "demo";
	}

	public static void main(String[] args) {
		AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(Application.class);
		Object bean = ac.getBean("string");
		System.out.println(bean);
	}

}

如果可以引入各种类, 可以运行, 且运行后输出 demo 字符串, 则环境配置成功

处理常规问题

如果运行时提示如下内容, 可以从Gradle面板中spring-core模块里 Tasks - other 下运行两个 build, cglibRepackJar 和 objenesisRepackJar

Kotlin: Classpath entry points to a non-existent location: C:\...\spring-source-5.2.13\spring-core\build\libs\spring-cglib-repack-3.3.0.jar
Kotlin: Classpath entry points to a non-existent location: C:\...\spring-source-5.2.13\spring-core\build\libs\spring-objenesis-repack-3.1.jar
Kotlin: warnings found and -Werror specified

如果提示如下内容, spring-core 模块下新建 lib 目录, 将 spring-core/ktolin-coroutines/build/libs/kotlin-coroutines-5.2.13.RELEASE.jar 拷贝到新建的 lib 目录, 然后在 spring-core 模块的 gradle 配置文件中添加该 jar 的依赖(在 dependencies 中添加 compile fileTree(dir:'lib',includes:['*jar'])), 然后重新运行

C:\mrathena\develop\workspace\idea\mrathena\study\spring-source-5.2.13\spring-core\src\main\java\org\springframework\core\ReactiveAdapterRegistry.java:350:31
java: 找不到符号
  符号:   变量 CoroutinesUtils
  位置: 类 org.springframework.core.ReactiveAdapterRegistry.CoroutinesRegistrar

如果提示如下内容, 在 spring-context 模块的 gradle 配置文件中修改 spring-instrument 的依赖, 从 optional 改成 compile

C:\mrathena\develop\workspace\idea\mrathena\study\spring-source-5.2.13\spring-context\src\main\java\org\springframework\context\weaving\DefaultContextLoadTimeWeaver.java:26:38
java: 找不到符号
  符号:   类 InstrumentationSavingAgent
  位置: 程序包 org.springframework.instrument

C:\mrathena\develop\workspace\idea\mrathena\study\spring-source-5.2.13\spring-context\src\main\java\org\springframework\instrument\classloading\InstrumentationLoadTimeWeaver.java:162:20
java: 找不到符号
  符号:   变量 InstrumentationSavingAgent
  位置: 类 org.springframework.instrument.classloading.InstrumentationLoadTimeWeaver.InstrumentationAccessor

处理 AspectJ 问题

听说你还没学Spring就被源码编译劝退了?30+张图带你玩转Spring编译

需要额外引入 compile(project(":spring-aspects"))

找不到符号:类 JCacheCacheAspect、JtaAnnotationTransactionAspect、AnnotationTransactionAspect 、AnnotationCacheAspect 、AnnotationAsyncExecutionAspect 、AnnotationBeanConfigurerAspect 等, 这些文件都是 .aj 格式, 需要用 AspectJ 编译器 Ajc 来编译

参考引用文章的第七点, 注意勾选 “Delegate to Javac”, 这样只有 .aj 的会被 Ajc 编译器编译, 其他的 .java 还是 javac 编译器编译, 不然所有类都用ajc编译, 导致aop中解析切面时判定为不是切面, 引起误解. BeanFactoryAspectJAdvisorsBuilder#buildAspectJAdvisors 的 isAspect 方法. 而且ajc编译器无法和lombok协同工作, 所以lombok引入的log是识别不了的(虽然可以换成 private static final Logger log = LoggerFactory.getLogger(CalculateAspect.class);)

搞完以后可能一些 test 还是会报错, 把对应的 test 里面报错的方法或注解给他注释掉就好了. 包括但不限于 注释掉/加public等. 实在不行可以把 test 都删掉

Build -> Build Project, 如果出现其他异常情况, 可以尝试多 build 几次, 很可能就成功了

生成代理类 class

System.getProperties().put("sun.misc.ProxyGenerator.saveGeneratedFiles", "true");

在项目下(不是模块下)生成 com/sun/proxy $Proxy0.class

提交代码

如果需要将编译好的工程提交到git仓库, 以便于后续使用, 那么需要将 .gitignore 里面的 target/ 移除掉, 因为 spring-aop 模块的源码中有一个包路径 org.springframework.aop.target, 如果屏蔽 target, 则该包下的包和类全都不会被提交

问题

在这里插入图片描述

源码导入到 idea 后, 经过各种尝试, 多次 build, 各模块之间的依赖仍然无法引入, 不知道为什么, 尝试导入十多次, 偶尔成功一次

新建的用于测试的Gradle模块里, 无法在类上添加@Configuration注解, 因为没有依赖到

因为我的idea的配置是从旧的idea导入的, 有些配置的路径发生了变化, 虽然重新配置过了, 但是运行spirng源码的时候偶尔还是提示kotlin从旧的jdk目录下引入了一个不存在的jar, 导致运行失败

干脆直接重置了idea的配置, 重新搞了多遍, 发现各种奇怪的问题都没有了, 每次都是一步到位, 导入spring源码成功

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值