banner输出的方式
1、默认banner输出
就是spring boot
2、文字banner
修改banner图
在resources下创建banner.txt 。内容为
/*
_ooOoo_
o8888888o
88" . "88
(| -_- |)
O\ = /O
____/`---'\____
.' \\| |// `.
/ \\||| : |||// \
/ _||||| -:- |||||- \
| | \\\ - /// | |
| \_| ''\---/'' | |
\ .-\__ `-` ___/-. /
___`. .' /--.--\ `. . __
."" '< `.___\_<|>_/___.' >'"".
| | : `- \`.;`\ _ /`;.`/ - ` : | |
\ \ `-. \_ __\ /__ _/ .-` / /
======`-.____`-.___\_____/___.-`____.-'======
`=---='
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
佛祖保佑 永无BUG
*/
然后运行SpringBoot项目
可以看到打印已经变了
将banner.txt 修改为favorite.txt , 这样就没有效果了,需要在
application.properties 配置spring.banner.location=favorite.txt才有效果。
3、图片banner
使用图片做banner
在resources下创建banner.jpg
启动项目后打印效果如下:
如果将banner.jpg改成favorite.jpg执行在application.properties 中设置spring.banner.image.location=favorite.jpg
4、兜底banner
使用代码配置banner
public class Sb2Application {
public static void main(String[] args) {
SpringApplication springApplication = new SpringApplication(Sb2Application.class);
springApplication.setBanner(new ResourceBanner(new ClassPathResource("favorite.txt")));
springApplication.addListeners(new SecondListener());
springApplication.run(args);
}
}
5、关闭banner的打印
在application.properties配置如下
spring.main.banner-mode=off
banner原理解析
首先进入Application的main函数启动入口的run方法
SpringApplication这个类
public static ConfigurableApplicationContext run(Class<?> primarySource, String... args) {
return run(new Class<?>[] { primarySource }, args);
}
//new SpringApplication(primarySources)这个咱们不用看,里面是springboot自动装配(SPI)的逻辑,咱们直接看后面的run(args)
public static ConfigurableApplicationContext run(Class<?>[] primarySources, String[] args) {
return new SpringApplication(primarySources).run(args);
}
public ConfigurableApplicationContext run(String... args) {
StopWatch stopWatch = new StopWatch();
stopWatch.start();
ConfigurableApplicationContext context = null;
Collection<SpringBootExceptionReporter> exceptionReporters = new ArrayList<>();
configureHeadlessProperty();
SpringApplicationRunListeners listeners = getRunListeners(args);
listeners.starting();
try {
ApplicationArguments applicationArguments = new DefaultApplicationArguments(args);
ConfigurableEnvironment environment = prepareEnvironment(listeners, applicationArguments);
configureIgnoreBeanInfo(environment); //我们发现这一步是处理启动banner的逻辑,点进去看看
Banner printedBanner = printBanner(environment);
context = createApplicationContext();
exceptionReporters = getSpringFactoriesInstances(SpringBootExceptionReporter.class,
new Class[] { ConfigurableApplicationContext.class }, context);
prepareContext(context, environment, listeners, applicationArguments, printedBanner);
refreshContext(context);
afterRefresh(context, applicationArguments);
stopWatch.stop();
if (this.logStartupInfo) {
new StartupInfoLogger(this.mainApplicationClass).logStarted(getApplicationLog(), stopWatch);
}
listeners.started(context);
callRunners(context, applicationArguments);
}
catch (Throwable ex) {
handleRunFailure(context, ex, exceptionReporters, listeners);
throw new IllegalStateException(ex);
}
try {
listeners.running(context);
}
catch (Throwable ex) {
handleRunFailure(context, ex, exceptionReporters, null);
throw new IllegalStateException(ex);
}
return context;
}
banner处理逻辑
private Banner printBanner(ConfigurableEnvironment environment) {
if (this.bannerMode == Banner.Mode.OFF) {
return null;
}
ResourceLoader resourceLoader = (this.resourceLoader != null) ? this.resourceLoader
: new DefaultResourceLoader(getClassLoader());
SpringApplicationBannerPrinter bannerPrinter = new SpringApplicationBannerPrinter(resourceLoader, this.banner);
if (this.bannerMode == Mode.LOG) {
return bannerPrinter.print(environment, this.mainApplicationClass, logger);
} //banner没有关闭且没有指定是写到log文件中的时候,会走到这一步
return bannerPrinter.print(environment, this.mainApplicationClass, System.out);
}
public Banner print(Environment environment, Class<?> sourceClass, PrintStream out) { //这里获取banner内容
Banner banner = getBanner(environment);
banner.printBanner(environment, sourceClass, out);
return new PrintedBanner(banner, sourceClass);
}
private Banner getBanner(Environment environment) {
Banners banners = new Banners(); //我们没有配置最骚气的图片类型的banner内容(做人要含蓄一点),所以我们看下一步
banners.addIfNotNull(getImageBanner(environment)); //我们配置的是文本型的banner,所以看这里的getTextBanner(environment)
banners.addIfNotNull(getTextBanner(environment));
if (banners.hasAtLeastOneBanner()) {
return banners;
}
if (this.fallbackBanner != null) {
return this.fallbackBanner;
}
return DEFAULT_BANNER;
}
//到这里同学应该就知道原理了
private Banner getTextBanner(Environment environment) { //拿到自定义配置的banner文件地址
String location = environment.getProperty(BANNER_LOCATION_PROPERTY, DEFAULT_BANNER_LOCATION);
Resource resource = this.resourceLoader.getResource(location);
if (resource.exists()) {
return new ResourceBanner(resource);
}
return null;
}
//DEFAULT_BANNER_LOCATION常量就指向了banner.txt文件
static final String DEFAULT_BANNER_LOCATION = "banner.txt";