Skip to content

Commit 01ec5d8

Browse files
committed
Polishing
1 parent 6e579b0 commit 01ec5d8

File tree

6 files changed

+81
-95
lines changed

6 files changed

+81
-95
lines changed

spring-aop/src/main/java/org/springframework/aop/framework/ProxyFactoryBean.java

Lines changed: 29 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2017 the original author or authors.
2+
* Copyright 2002-2020 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -21,9 +21,7 @@
2121
import java.io.Serializable;
2222
import java.util.ArrayList;
2323
import java.util.Arrays;
24-
import java.util.HashMap;
2524
import java.util.List;
26-
import java.util.Map;
2725

2826
import org.aopalliance.aop.Advice;
2927
import org.aopalliance.intercept.Interceptor;
@@ -334,11 +332,8 @@ private synchronized Object newPrototypeInstance() {
334332
// an independent instance of the configuration.
335333
// In this case, no proxy will have an instance of this object's configuration,
336334
// but will have an independent copy.
337-
if (logger.isTraceEnabled()) {
338-
logger.trace("Creating copy of prototype ProxyFactoryBean config: " + this);
339-
}
340-
341335
ProxyCreatorSupport copy = new ProxyCreatorSupport(getAopProxyFactory());
336+
342337
// The copy needs a fresh advisor chain, and a fresh TargetSource.
343338
TargetSource targetSource = freshTargetSource();
344339
copy.copyConfigurationFrom(this, targetSource, freshAdvisorChain());
@@ -349,9 +344,6 @@ private synchronized Object newPrototypeInstance() {
349344
}
350345
copy.setFrozen(this.freezeProxy);
351346

352-
if (logger.isTraceEnabled()) {
353-
logger.trace("Using ProxyCreatorSupport copy: " + copy);
354-
}
355347
return getProxy(copy.createAopProxy());
356348
}
357349

@@ -438,16 +430,12 @@ private synchronized void initializeAdvisorChain() throws AopConfigException, Be
438430

439431
// Materialize interceptor chain from bean names.
440432
for (String name : this.interceptorNames) {
441-
if (logger.isTraceEnabled()) {
442-
logger.trace("Configuring advisor or advice '" + name + "'");
443-
}
444-
445433
if (name.endsWith(GLOBAL_SUFFIX)) {
446434
if (!(this.beanFactory instanceof ListableBeanFactory)) {
447435
throw new AopConfigException(
448436
"Can only use global advisors or interceptors with a ListableBeanFactory");
449437
}
450-
addGlobalAdvisor((ListableBeanFactory) this.beanFactory,
438+
addGlobalAdvisors((ListableBeanFactory) this.beanFactory,
451439
name.substring(0, name.length() - GLOBAL_SUFFIX.length()));
452440
}
453441

@@ -464,7 +452,7 @@ private synchronized void initializeAdvisorChain() throws AopConfigException, Be
464452
// Avoid unnecessary creation of prototype bean just for advisor chain initialization.
465453
advice = new PrototypePlaceholderAdvisor(name);
466454
}
467-
addAdvisorOnChainCreation(advice, name);
455+
addAdvisorOnChainCreation(advice);
468456
}
469457
}
470458
}
@@ -487,11 +475,10 @@ private List<Advisor> freshAdvisorChain() {
487475
if (logger.isDebugEnabled()) {
488476
logger.debug("Refreshing bean named '" + pa.getBeanName() + "'");
489477
}
490-
// Replace the placeholder with a fresh prototype instance resulting
491-
// from a getBean() lookup
478+
// Replace the placeholder with a fresh prototype instance resulting from a getBean lookup
492479
if (this.beanFactory == null) {
493-
throw new IllegalStateException("No BeanFactory available anymore (probably due to serialization) " +
494-
"- cannot resolve prototype advisor '" + pa.getBeanName() + "'");
480+
throw new IllegalStateException("No BeanFactory available anymore (probably due to " +
481+
"serialization) - cannot resolve prototype advisor '" + pa.getBeanName() + "'");
495482
}
496483
Object bean = this.beanFactory.getBean(pa.getBeanName());
497484
Advisor refreshedAdvisor = namedBeanToAdvisor(bean);
@@ -508,28 +495,26 @@ private List<Advisor> freshAdvisorChain() {
508495
/**
509496
* Add all global interceptors and pointcuts.
510497
*/
511-
private void addGlobalAdvisor(ListableBeanFactory beanFactory, String prefix) {
498+
private void addGlobalAdvisors(ListableBeanFactory beanFactory, String prefix) {
512499
String[] globalAdvisorNames =
513500
BeanFactoryUtils.beanNamesForTypeIncludingAncestors(beanFactory, Advisor.class);
514501
String[] globalInterceptorNames =
515502
BeanFactoryUtils.beanNamesForTypeIncludingAncestors(beanFactory, Interceptor.class);
516-
List<Object> beans = new ArrayList<Object>(globalAdvisorNames.length + globalInterceptorNames.length);
517-
Map<Object, String> names = new HashMap<Object, String>(beans.size());
518-
for (String name : globalAdvisorNames) {
519-
Object bean = beanFactory.getBean(name);
520-
beans.add(bean);
521-
names.put(bean, name);
522-
}
523-
for (String name : globalInterceptorNames) {
524-
Object bean = beanFactory.getBean(name);
525-
beans.add(bean);
526-
names.put(bean, name);
527-
}
528-
AnnotationAwareOrderComparator.sort(beans);
529-
for (Object bean : beans) {
530-
String name = names.get(bean);
531-
if (name.startsWith(prefix)) {
532-
addAdvisorOnChainCreation(bean, name);
503+
if (globalAdvisorNames.length > 0 || globalInterceptorNames.length > 0) {
504+
List<Object> beans = new ArrayList<Object>(globalAdvisorNames.length + globalInterceptorNames.length);
505+
for (String name : globalAdvisorNames) {
506+
if (name.startsWith(prefix)) {
507+
beans.add(beanFactory.getBean(name));
508+
}
509+
}
510+
for (String name : globalInterceptorNames) {
511+
if (name.startsWith(prefix)) {
512+
beans.add(beanFactory.getBean(name));
513+
}
514+
}
515+
AnnotationAwareOrderComparator.sort(beans);
516+
for (Object bean : beans) {
517+
addAdvisorOnChainCreation(bean);
533518
}
534519
}
535520
}
@@ -540,17 +525,11 @@ private void addGlobalAdvisor(ListableBeanFactory beanFactory, String prefix) {
540525
* Because of these three possibilities, we can't type the signature
541526
* more strongly.
542527
* @param next advice, advisor or target object
543-
* @param name bean name from which we obtained this object in our owning
544-
* bean factory
545528
*/
546-
private void addAdvisorOnChainCreation(Object next, String name) {
529+
private void addAdvisorOnChainCreation(Object next) {
547530
// We need to convert to an Advisor if necessary so that our source reference
548531
// matches what we find from superclass interceptors.
549-
Advisor advisor = namedBeanToAdvisor(next);
550-
if (logger.isTraceEnabled()) {
551-
logger.trace("Adding advisor with name '" + name + "'");
552-
}
553-
addAdvisor(advisor);
532+
addAdvisor(namedBeanToAdvisor(next));
554533
}
555534

556535
/**
@@ -561,9 +540,7 @@ private void addAdvisorOnChainCreation(Object next, String name) {
561540
*/
562541
private TargetSource freshTargetSource() {
563542
if (this.targetName == null) {
564-
if (logger.isTraceEnabled()) {
565-
logger.trace("Not refreshing target: Bean name not specified in 'interceptorNames'.");
566-
}
543+
// Not refreshing target: bean name not specified in 'interceptorNames'
567544
return this.targetSource;
568545
}
569546
else {
@@ -591,8 +568,8 @@ private Advisor namedBeanToAdvisor(Object next) {
591568
// We expected this to be an Advisor or Advice,
592569
// but it wasn't. This is a configuration error.
593570
throw new AopConfigException("Unknown advisor type " + next.getClass() +
594-
"; Can only include Advisor or Advice type beans in interceptorNames chain except for last entry," +
595-
"which may also be target or TargetSource", ex);
571+
"; can only include Advisor or Advice type beans in interceptorNames chain " +
572+
"except for last entry which may also be target instance or TargetSource", ex);
596573
}
597574
}
598575

@@ -603,7 +580,7 @@ private Advisor namedBeanToAdvisor(Object next) {
603580
protected void adviceChanged() {
604581
super.adviceChanged();
605582
if (this.singleton) {
606-
logger.debug("Advice has changed; recaching singleton instance");
583+
logger.debug("Advice has changed; re-caching singleton instance");
607584
synchronized (this) {
608585
this.singletonInstance = null;
609586
}

spring-context/src/main/java/org/springframework/context/annotation/Configuration.java

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2019 the original author or authors.
2+
* Copyright 2002-2020 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -343,15 +343,16 @@
343343
*
344344
* <p>By default, {@code @Bean} methods will be <em>eagerly instantiated</em> at container
345345
* bootstrap time. To avoid this, {@code @Configuration} may be used in conjunction with
346-
* the {@link Lazy @Lazy} annotation to indicate that all {@code @Bean} methods declared within
347-
* the class are by default lazily initialized. Note that {@code @Lazy} may be used on
348-
* individual {@code @Bean} methods as well.
346+
* the {@link Lazy @Lazy} annotation to indicate that all {@code @Bean} methods declared
347+
* within the class are by default lazily initialized. Note that {@code @Lazy} may be used
348+
* on individual {@code @Bean} methods as well.
349349
*
350350
* <h2>Testing support for {@code @Configuration} classes</h2>
351351
*
352352
* <p>The Spring <em>TestContext framework</em> available in the {@code spring-test} module
353353
* provides the {@code @ContextConfiguration} annotation which can accept an array of
354-
* {@code @Configuration} {@code Class} objects:
354+
* <em>component class</em> references &mdash; typically {@code @Configuration} or
355+
* {@code @Component} classes.
355356
*
356357
* <pre class="code">
357358
* &#064;RunWith(SpringRunner.class)

spring-context/src/main/java/org/springframework/context/annotation/PropertySource.java

Lines changed: 33 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2018 the original author or authors.
2+
* Copyright 2002-2020 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -54,25 +54,30 @@
5454
* }
5555
* }</pre>
5656
*
57-
* Notice that the {@code Environment} object is
57+
* <p>Notice that the {@code Environment} object is
5858
* {@link org.springframework.beans.factory.annotation.Autowired @Autowired} into the
5959
* configuration class and then used when populating the {@code TestBean} object. Given
6060
* the configuration above, a call to {@code testBean.getName()} will return "myTestBean".
6161
*
62-
* <h3>Resolving ${...} placeholders in {@code <bean>} and {@code @Value} annotations</h3>
63-
*
64-
* In order to resolve ${...} placeholders in {@code <bean>} definitions or {@code @Value}
65-
* annotations using properties from a {@code PropertySource}, one must register
66-
* a {@code PropertySourcesPlaceholderConfigurer}. This happens automatically when using
67-
* {@code <context:property-placeholder>} in XML, but must be explicitly registered using
68-
* a {@code static} {@code @Bean} method when using {@code @Configuration} classes. See
69-
* the "Working with externalized values" section of @{@link Configuration}'s javadoc and
70-
* "a note on BeanFactoryPostProcessor-returning @Bean methods" of @{@link Bean}'s javadoc
71-
* for details and examples.
62+
* <h3>Resolving <code>${...}</code> placeholders in {@code <bean>} and {@code @Value} annotations</h3>
63+
*
64+
* <p>In order to resolve ${...} placeholders in {@code <bean>} definitions or {@code @Value}
65+
* annotations using properties from a {@code PropertySource}, you must ensure that an
66+
* appropriate <em>embedded value resolver</em> is registered in the {@code BeanFactory}
67+
* used by the {@code ApplicationContext}. This happens automatically when using
68+
* {@code <context:property-placeholder>} in XML. When using {@code @Configuration} classes
69+
* this can be achieved by explicitly registering a {@code PropertySourcesPlaceholderConfigurer}
70+
* via a {@code static} {@code @Bean} method. Note, however, that explicit registration
71+
* of a {@code PropertySourcesPlaceholderConfigurer} via a {@code static} {@code @Bean}
72+
* method is typically only required if you need to customize configuration such as the
73+
* placeholder syntax, etc. See the "Working with externalized values" section of
74+
* {@link Configuration @Configuration}'s javadocs and "a note on
75+
* BeanFactoryPostProcessor-returning {@code @Bean} methods" of {@link Bean @Bean}'s
76+
* javadocs for details and examples.
7277
*
7378
* <h3>Resolving ${...} placeholders within {@code @PropertySource} resource locations</h3>
7479
*
75-
* Any ${...} placeholders present in a {@code @PropertySource} {@linkplain #value()
80+
* <p>Any ${...} placeholders present in a {@code @PropertySource} {@linkplain #value()
7681
* resource location} will be resolved against the set of property sources already
7782
* registered against the environment. For example:
7883
*
@@ -92,7 +97,7 @@
9297
* }
9398
* }</pre>
9499
*
95-
* Assuming that "my.placeholder" is present in one of the property sources already
100+
* <p>Assuming that "my.placeholder" is present in one of the property sources already
96101
* registered, e.g. system properties or environment variables, the placeholder will
97102
* be resolved to the corresponding value. If not, then "default/path" will be used as a
98103
* default. Expressing a default value (delimited by colon ":") is optional. If no
@@ -101,10 +106,10 @@
101106
*
102107
* <h3>A note on property overriding with @PropertySource</h3>
103108
*
104-
* In cases where a given property key exists in more than one {@code .properties}
109+
* <p>In cases where a given property key exists in more than one {@code .properties}
105110
* file, the last {@code @PropertySource} annotation processed will 'win' and override.
106111
*
107-
* For example, given two properties files {@code a.properties} and
112+
* <p>For example, given two properties files {@code a.properties} and
108113
* {@code b.properties}, consider the following two configuration classes
109114
* that reference them with {@code @PropertySource} annotations:
110115
*
@@ -118,7 +123,7 @@
118123
* public class ConfigB { }
119124
* </pre>
120125
*
121-
* The override ordering depends on the order in which these classes are registered
126+
* <p>The override ordering depends on the order in which these classes are registered
122127
* with the application context.
123128
*
124129
* <pre class="code">
@@ -128,12 +133,12 @@
128133
* ctx.refresh();
129134
* </pre>
130135
*
131-
* In the scenario above, the properties in {@code b.properties} will override any
136+
* <p>In the scenario above, the properties in {@code b.properties} will override any
132137
* duplicates that exist in {@code a.properties}, because {@code ConfigB} was registered
133138
* last.
134139
*
135140
* <p>In certain situations, it may not be possible or practical to tightly control
136-
* property source ordering when using {@code @ProperySource} annotations. For example,
141+
* property source ordering when using {@code @PropertySource} annotations. For example,
137142
* if the {@code @Configuration} classes above were registered via component-scanning,
138143
* the ordering is difficult to predict. In such cases - and if overriding is important -
139144
* it is recommended that the user fall back to using the programmatic PropertySource API.
@@ -150,6 +155,7 @@
150155
* @author Chris Beams
151156
* @author Juergen Hoeller
152157
* @author Phillip Webb
158+
* @author Sam Brannen
153159
* @since 3.1
154160
* @see PropertySources
155161
* @see Configuration
@@ -164,17 +170,21 @@
164170
public @interface PropertySource {
165171

166172
/**
167-
* Indicate the name of this property source. If omitted, a name will
168-
* be generated based on the description of the underlying resource.
173+
* Indicate the name of this property source. If omitted, the {@link #factory()}
174+
* will generate a name based on the underlying resource (in the case of
175+
* {@link org.springframework.core.io.support.DefaultPropertySourceFactory}:
176+
* derived from the resource description through a corresponding name-less
177+
* {@link org.springframework.core.io.support.ResourcePropertySource} constructor).
169178
* @see org.springframework.core.env.PropertySource#getName()
170179
* @see org.springframework.core.io.Resource#getDescription()
171180
*/
172181
String name() default "";
173182

174183
/**
175184
* Indicate the resource location(s) of the properties file to be loaded.
176-
* For example, {@code "classpath:/com/myco/app.properties"} or
177-
* {@code "file:/path/to/file"}.
185+
* <p>Both traditional and XML-based properties file formats are supported
186+
* &mdash; for example, {@code "classpath:/com/myco/app.properties"}
187+
* or {@code "file:/path/to/file.xml"}.
178188
* <p>Resource location wildcards (e.g. *&#42;/*.properties) are not permitted;
179189
* each location must evaluate to exactly one {@code .properties} resource.
180190
* <p>${...} placeholders will be resolved against any/all property sources already

spring-core/src/main/java/org/springframework/core/io/support/PropertySourceFactory.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2016 the original author or authors.
2+
* Copyright 2002-2020 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -32,6 +32,8 @@ public interface PropertySourceFactory {
3232
/**
3333
* Create a {@link PropertySource} that wraps the given resource.
3434
* @param name the name of the property source
35+
* (can be {@code null} in which case the factory implementation
36+
* will have to generate a name based on the given resource)
3537
* @param resource the resource (potentially encoded) to wrap
3638
* @return the new {@link PropertySource} (never {@code null})
3739
* @throws IOException if resource resolution failed

0 commit comments

Comments
 (0)