Before this commit, the Jetty connector did not have any
safeguard against multiple body subscriptions. Such as check has now
been added.
See gh-32100
Closes gh-32101
This commit ensures that setting the Content-Length through
setHeader("Content-Length", x") has the same effect as calling
setContentLength in the ShallowEtagHeaderFilter. It also filters out
Content-Type headers similarly to Content-Length.
See gh-32039
Closes gh-32051
This commit adds CORS support for Private Network Access
by adding an Access-Control-Allow-Private-Network response
header when the preflight request is sent with an
Access-Control-Request-Private-Network header and that
Private Network Access has been enabled in the CORS
configuration.
See https://developer.chrome.com/blog/private-network-access-preflight/
for more details.
Closes gh-31974
(cherry picked from commit 318d460256)
Includes TypeVariable bypass for reflection-free annotation retrieval.
Includes info log message for annotation attribute retrieval failure.
Closes gh-27182
(cherry picked from commit 70247c4a94)
Prior to this commit, the AnnotationsScanner used in the
MergedAnnotations infrastructure found duplicate annotations on methods
within multi-level interface hierarchies.
This commit addresses this issue by scanning methods at a given level
in the interface hierarchy using ReflectionUtils#getDeclaredMethods
instead of Class#getMethods, since the latter includes public methods
declared in super-interfaces which will anyway be scanned when
processing super-interfaces recursively.
Closes gh-31803
(cherry picked from commit 75da9c3c47)
(cherry picked from commit 1e742aae34)
This commit supports the scroll() and scroll(ScrollMode) methods from
Hibernate's Query API in SharedEntityManagerCreator's query-terminating
methods set.
See gh-31682
Closes gh-31684
Prior to this commit, the Jackson 2.x encoders, in case of encoding a
stream of data, would first release the `ByteArrayBuilder` and then the
`JsonGenerator`. This order is inconsistent with the single value
variant (see `o.s.h.codec.json.AbstractJackson2Encoder#encodeValue`) and
invalid since the `JsonGenerator` uses internally the
`ByteArrayBuilder`.
In case of a CSV Encoder, the codec can buffer data to write the column
names of the CSV file. Writing an empty Flux with this Encoder would not
fail but still log a NullPointerException ignored by the reactive
pipeline.
This commit fixes the order and avoid such issues at runtime.
Fixes gh-31657
This commit updates PathMatchingResourcePatternResolver to avoid
returning duplicate resources on MS Windows when searching using the
`classpath*:` prefix and a wildcard pattern that matches resources
which are directly present in a JAR as well as present via classpath
manifest entries.
See gh-31598
Closes gh-31603
(cherry picked from commit d5874ab99e)
This is necessary for compatibility with Log4J 2.21, analogous to the existing re-resolution in Spring's SLF4J adapter.
Closes gh-31582
(cherry picked from commit 1e78cc35e5)
Previously, MessagingMessageListenerAdapter or any adapter relying on
the default MessagingMessageConverter would log an incoming message
with a toString of the Message that does not provide any extra
information. This is due to the default implementation providing a
lazy resolution message that only attempts to extract the payload
when necessary.
This commit implements a toString method that uses the raw JMS message
if the payload is not available. If it is, the payload is used instead.
Closes gh-21265
(cherry picked from commit a37abd5e54)
This commit refines CORS wildcard processing Javadoc to
provides more details on how wildcards are handled for
Access-Control-Allow-Methods, Access-Control-Allow-Headers
and Access-Control-Expose-Headers CORS headers.
For Access-Control-Expose-Headers, it is not possible to copy
the response headers which are not available at the point
when the CorsProcessor is invoked. Since all the major browsers
seem to support wildcard including on requests with credentials,
and since this is ultimately the user-agent responsibility to
check on client-side what is authorized or not, Spring Framework
continues to support this use case.
See gh-31168
gh-30811 introduced explicit support for collections and maps in
ObjectUtils.nullSafeConciseToString() by invoking isEmpty() on a Map or
Collection to determine which concise string representation should be
used. However, this caused a regression in which an exception was
thrown if the Map or Collection was a proxy generated by
AbstractFactoryBean to support <util:set />, <util:list />, and
<util:map /> in XML configuration.
This commit addresses this set of regressions by always returning
"[...]" or "{...}" for a Collection or Map, respectively, disregarding
whether the map is empty or not.
Closes gh-31156
This commit optimizes ClassUtils#getMostSpecificMethod which is
a method frequently invoked in typical Spring applications.
It refines ClassUtils#isOverridable by considering static and
final modifiers as non overridable and optimizes its implementation.
Closes gh-31100
Beginning with Java 16, inner classes may contain static members. We
therefore need to search for @DynamicPropertySource methods in the
current class after searching enclosing classes so that a local
@DynamicPropertySource method can override properties registered in an
enclosing class.
However, since Spring Framework 5.3.x is built using Java 8, this
commit removes DynamicPropertySourceOverridesEnclosingClassTests since
it declares a static method in a @Nested (inner) test class, which
results in a compiler error on Java 8.
See https://bugs.openjdk.org/browse/JDK-8254321
See gh-31085
Prior to this commit, a dynamic property registered via a
@DynamicPropertySource method in a @Nested test class was not able to
override a property registered via a @DynamicPropertySource method in
the enclosing class.
See gh-26091
Closes gh-31083
Reuses ValidationAnnotationUtils which is slightly optimized for the detection of Spring's Validated annotation now, also to the benefit of common web scenarios.
Closes gh-21852
(cherry picked from commit c7269feeaa)
Aligned with shortcut handling in AutowiredAnnotationBeanPostProcessor.
Includes minor MethodInvoker optimization for pre-resolved targetClass.
Closes gh-30883
(cherry picked from commit 6183f06846)
Prior to this commit, there was no explicit support for arrays,
collections, and maps in nullSafeConciseToString(). This lead to string
representations such as the following, regardless of whether the array,
collection, or map was empty.
- char[]@1623b78d
- java.util.ImmutableCollections$List12@74fe5c40
- java.util.ImmutableCollections$MapN@10e31a9a
This commit introduces explicit support for arrays, collections, and
maps in nullSafeConciseToString(), which results in the following
empty/non-empty string representations.
- array: {} / {...}
- collection: [] / [...]
- map: {} / {...}
The reason a string representation of an array uses "{}" instead of
"[]" (like in Arrays.toString(...)) is that
ObjectUtils.nullSafeToString(<array>) already follows that convention,
and the implementation of nullSafeConciseToString() aligns with that
for the sake of consistency.
Closes gh-30811
We would preferably use ObjectUtils.nullSafeConciseToString(rejectedValue) here but revert to the full nullSafeToString representation for strict backwards compatibility (programmatic toString calls as well as exception messages).
Closes gh-30799
(cherry picked from commit 1dc9dffc70)
In addition to the previously addressed removal of bean definitions, this is able to deal with prototype factory methods returning non-null after null or also null after non-null. Stale cached values are getting refreshed rather than bypassed.
Closes gh-30794
(cherry picked from commit 0226580773)
This commit extends the list of explicitly supported types in
ObjectUtils.nullSafeConciseToString() with the following.
- Optional
- File
- Path
- InetAddress
- Charset
- Currency
- TimeZone
- ZoneId
- Pattern
Closes gh-30806
Since EclipseLink applies a custom transaction isolation value to its shared DatabasePlatform instance, we need to immediately restore the original value after the current value got picked up for JDBC Connection access inside of EclipseLink. In order to not interfere with concurrent transactions, we need to use synchronization around the transaction begin sequence in such a case.
Closes gh-29997
Includes hashCode optimization in AbstractBeanFactoryBasedTargetSource.
Includes ThreadLocal naming fix in ThreadLocalTargetSource.
Closes gh-30576
Closes gh-30581
(cherry picked from commit c68552556f)
Environment.acceptsProfiles(String...) was deprecated in 5.1 in
conjunction with gh-17063 which introduced a new
acceptsProfiles(Profiles) method to replace it. The deprecated method
only supports OR semantics; whereas, the new method supports profile
expressions. Thus, the goal was to encourage people to use the more
powerful profile expressions instead of the limited OR support with
profile names.
However, there are use cases where it is difficult (if not impossible)
to provide a Profiles instance, and there are use cases where it is
simply preferable to provide profile expressions directly as strings.
To address these issues, this commit introduces a new matchesProfiles()
method in Environment that accepts a var-args list of profile
expressions.
See gh-30206
Closes gh-30226
Prior to gh-30325, supplying a null reference for a SpEL expression was
effectively equivalent to supplying the String "null" as the
expression. Consequently, evaluation of a null reference expression
always evaluated to a null reference. However, that was accidental
rather than by design.
Due to the introduction of the checkExpressionLength(String) method in
InternalSpelExpressionParser (in conjunction with gh-30325), an attempt
to evaluate a null reference as a SpEL expression now results in a
NullPointerException.
To address both of these issues,
TemplateAwareExpressionParser.parseExpression() and
SpelExpressionParser.parseRaw() now reject null and empty SpEL
expressions.
See gh-30371
Closes gh-30373
This commit introduces infrastructure to differentiate between
programmatic setting of a variable in an EvaluationContext versus the
assignment of a variable within a SpEL expression using the assignment
operator (=). In addition, this commit disables variable assignment
within expressions when using the SimpleEvaluationContext.
Closes gh-30327
This commit introduces support for limiting the maximum length of a
string resulting from the concatenation operator (+) in SpEL
expressions.
Closes gh-30331
This commit changes the max regex length in SpEL expressions from 1024
to 1000 in order to consistently use "round" numbers for recently
introduced limits.
See gh-30265
Sometime between JDK 8 and JDK 17, the behavior for List::toArray()
changed. Specifically, the type returned for List<String> changed from
String[] to Object[].
This commit therefore removes an assertion against this particular
JDK-specific behavior. The affected test method retains additional
assertions along the same lines but which are not flaky.
This commit ensures that HTTP headers like "text/event-stream"
are correctly forwarded to the converter used in
SseServerResponse for proper pretty print handling.
Close gh-30302
This commit increases the max regex length in SpEL expressions from 256
to 1024 in order to support use cases where a regex may be rather long
without necessarily increasing the complexity of the regex.
Closes gh-30298
ObjectUtils.nullSafeToString(Object) exists for generating a string
representation of various objects in a "null-safe" manner, including
support for object graphs, collections, etc.
However, there are times when we would like to generate a "concise",
null-safe string representation that does not include an entire object
graph (or potentially a collection of object graphs).
This commit introduces ObjectUtils.nullSafeConciseToString(Object) to
address this need and makes use of the new feature in FieldError and
ConversionFailedException.
Closes gh-30286
StringUtils.truncate() serves as central, consistent way for truncating
strings used in log messages and exception failure messages, for
immediate use in LogFormatUtils and ObjectUtils.
See gh-30286
Closes gh-30290
This commit changes the name of two recently introduced methods in the
`MockRestRequestMatchers` class for header and queryParam. These have
been found to cause false negatives in user tests, due to the new
overload taking precedence in some cases.
Namely, using a `Matcher` factory method which can apply to both `List`
and `String` will cause the compiler to select the newest list overload,
by instantiating a `Matcher<Object>`.
This can cause false negatives in user tests, failing tests that used
to pass because the Matcher previously applied to the first String in
the header or queryParam value list. For instance, `equalsTo("a")`.
The new overloads are recent enough and this has enough potential to
cause an arbitrary number of user tests to fail that we break the API
to eliminate the ambiguity, by renaming the methods with a `*List`
suffix.
See gh-30220
See gh-30238
Closes gh-30235
This commit updates AbstractMessageWriterResultHandler#writeBody in
order to use the declared bodyParameter instead of
ResolvableType.forInstance(body) when the former has unresolvable
generics.
Closes gh-30215
The `echoWebSocketHandler()` method is not defined in the
`WebSocketConfigurer` interface and should therefore be annotated with
`@Bean` instead of `@Override`.
Closes gh-30187
Prior to this commit, the EntityManager was not closed in
SharedEntityManagerCreator.DeferredQueryInvocationHandler's
invoke(Object, Method, Object[]) method if an invocation of
getOutputParameterValue(*) threw an exception other than
IllegalArgumentException, which could lead to a connection leak.
This commit addresses this by catching RuntimeException instead of
IllegalArgumentException.
Closes gh-30164
Supplying a large regular expression to the `matches` operator in a
SpEL expression can result in errors that are not very helpful to the
user.
This commit improves the diagnostics in SpEL for the `matches` operator
by throwing a SpelEvaluationException with a meaningful error message
to better assist the user.
Closes gh-30145
Attempting to create repeated text in a SpEL expression using the
repeat operator can result in errors that are not very helpful to the
user.
This commit improves the diagnostics in SpEL for the repeat operator by
throwing a SpelEvaluationException with a meaningful error message in
order to better assist the user.
Closes gh-30143
Prior to this commit, the pattern cache for the SpEL `matches` operator
only applied to expressions such as the following where the same
`matches` operator is invoked multiple times with different input:
"map.keySet().?[#this matches '.+xyz']"
The pattern cache did not apply to expressions such as the following
where the same pattern ('.+xyz') is used in multiple `matches`
operations:
"foo matches '.+xyz' AND bar matches '.+xyz'"
This commit addresses this by moving the instance of the pattern cache
map from OperatorMatches to InternalSpelExpressionParser so that the
cache can be reused for all `matches` operations for the given parser.
Closes gh-30141
This commit ensures that methods declared in java.lang.Object (such as
toString() can be invoked on a JDK proxy instance in a SpEL expression.
Closes gh-25316
Prior to this commit, the `RequestedContentTypeResolverBuilder` would
create a `RequestedContentTypeResolver` that internally delegates to a
list of resolvers. Each resolver would either return the list of
requested media types, or a singleton list with the "*/*" media type; in
this case this signals that the resolver cannot find a specific media
type requested and that we should continue with the next resolver in the
list.
Media Types returned by resolvers can contain parameters, such as the
quality factor. If the HTTP client requests "*/*;q=0.8", the
`HeaderContentTypeResolver` will return this as a singleton list. While
this has been resolved from the request, such a media type should not be
selected over other media types that could be returned by other
resolvers.
This commit changes the `RequestedContentTypeResolverBuilder` so that it
does not select "*/*;q=0.8" as the requested media type, but instead
continues delegating to other resolvers in the list. This means we need
to remove the quality factor before comparing it to the "*/*" for
equality check.
Fixes gh-30121
This commit ensures that SnakeYaml 2.0 is compatible at runtime with
Spring Framework 5.3.x with the `YamlProcessor` support.
The baseline version for SnakeYaml remains the same.
Closes gh-30097
Prior to this commit, using a dynamic `CaffeineCacheManager` would rely
on `ConcurrentHashMap#computeIfAbsent` for retrieving and creating cache
instances as needed. It turns out that using this method concurrently
can cause lock contention even when all known cache instances are
instantiated.
This commit avoids using this method if the cache instance already
exists and avoid storing `null` entries in the map. This change reduces
lock contention and the overall HashMap size in the non-dynamic case.
See gh-30066
Fixes gh-30085
We no longer have any JDK 5 related limitations imposed on us as was
the case when MetadataAwareAspectInstanceFactory was introduced; however,
MetadataAwareAspectInstanceFactory will remain as a specialized
sub-interface of AspectInstanceFactory.
Rationale: changes in org.springframework.aop.framework.autoproxy.target
were previously ignored since the "target" package was ignored by the
previous "eager" pattern for "target" folders.
This commit uses a local variable for the creation of a new JMS
Connection so that a rare failure in prepareConnection(...) does not
leave the connection field in a partially initialized state.
If such a JMSException occurs, the intermediary connection is closed.
This commit further defends against close() failures at that point,
by logging the close exception at DEBUG level. As a result, the original
JMSException is always re-thrown.
See gh-29116
Closes gh-30051
This commit adds a `header` variant and a `queryParam` variant to the
`MockRestRequestMatchers` API which take a single `Matcher` over the
list of values.
Contrary to the vararg variants, the whole list is evaluated and the
caller can choose the desired semantics using readily-available iterable
matchers like `everyItem`, `hasItems`, `hasSize`, `contains` or
`containsInAnyOrder`...
The fact that the previous variants don't strictly check the size of the
actual list == the number of provided matchers or expected values is
now documented in their respective javadocs.
See gh-29953
Closes gh-29964
Prior to this commit, the term "field" was sometimes used to refer to a
database column and sometimes used to refer to a bean property, which
lead to confusion in the Javadoc as well as within the code.
This commit addresses this by avoiding use of the term "field".
This change restricts the maximum number of forwards in MockMvcWebConnection to 100,
in case a forward is configured in a way that causes a loop. This is necessary in HtmlUnit
backed tests, unlike in classic MockMvc tests in which the forwards are not actually resolved.
See gh-29557
Closes gh-29866
Co-authored-by: Simon Baslé <sbasle@vmware.com>
When using R2dbcTransactionManager, connection will not be released if
it encounters error while doing `afterCleanup` steps. As `afterCleanup`
can use a database connection when doing `setAutoCommit(true)`, it can
fail under some conditions where the connection is not reliable.
This leads to the Connection not being released.
This commit ensures that inner steps of the `doCleanupAfterCompletion`
are protected against errors, logging the errors and continuing the
cleanup until the last step, which releases the connection.
Backport of commit e050c37
See gh-29703
Closes gh-29925
Co-authored-by: Simon Baslé <sbasle@vmware.com>
The previous commit changed the generated default name for a JMS
subscription to <FQCN>#<method name> -- for example:
- org.example.MyListener#myListenerMethod
However, the JMS spec does not guarantee that '#' is a supported
character. This commit therefore changes '#' to '.' as the separator
between the class name and method name -- for example:
- org.example.MyListener.myListenerMethod
This commit also introduces tests and documentation for these changes.
See gh-29902
Prior to this commit, when using durable subscribers with @JmsListener
methods that do not specify a custom subscription name the generated
default subscription name was always
org.springframework.jms.listener.adapter.MessagingMessageListenerAdapter.
Consequently, multiple such @JmsListener methods were assigned the
same subscription name which violates the uniqueness requirement.
To address this, MessagingMessageListenerAdapter now implements
SubscriptionNameProvider and generates the subscription name based on
the following rules.
- if the InvocableHandlerMethod is present, the subscription name will
take the form of handlerMethod.getBeanType().getName() + "#" +
handlerMethod.getMethod().getName().
- otherwise, getClass().getName() is used, which is analogous to the
previous behavior.
Closes gh-29902
Prior to this commit, we included Hibernate's Query.list() method in
SharedEntityManagerCreator's queryTerminatingMethods set but did not
include all of Hibernate's query-terminating methods.
To address this, this commit additionally includes the stream(),
uniqueResult(), and uniqueResultOptional() methods from Hibernate's
Query API in SharedEntityManagerCreator's query-terminating methods set.
Closes gh-29888
Though Jetty 10 was previously supported in the JettyClientHttpResponse,
this commit ensures support in the JettyClientHttpRequest.
Closes gh-29867
See gh-26123
This commit modifies the `DefaultDatabaseClient` implementation in order
to ensure lazier usage of the `Supplier<String>` passed to the sql
method (`DatabaseClient#sql(Supplier)`).
Since technically `DatabaseClient` is an interface that could have 3rd
party implementations, the lazyness expectation is only hinted at in the
`DatabaseClient#sql` javadoc.
Possible caveat: some log statements attempt to reflect the now lazily
resolved SQL string. Similarly, some exceptions can capture the SQL that
caused the issue if known. We expect that these always occur after the
execution of the statement has been attempted (see `ResultFunction`).
At this point the SQL string will be accessible and logs and exceptions
should reflect it as before. Keep an eye out for such strings turning
into `null` after this change, which would indicate the opposite.
Backport of d72df5ace4
See gh-29367
Closes gh-29887
This commit changes the FatalBeanException previously thrown for
an IllegalArgumentException which seems more suitable for that
use case.
Closes gh-29860
When comparing empty ProducesRequestCondition, compareTo would throw an
IllegalStateException if the Accept header was invalid. This commit
fixes that behavior.
See gh-29794
Closes gh-29836
When logging the current connection inside R2dbcTransactionManager
doBegin, the mono object was logged instead of the connection lambda
parameter.
Other similar debug-level logs do use the actual Connection object,
so this commit does the same.
Backport of gh-29800
Closes gh-29824
Prior to this commit, extracting the path within handler mapping would
result in "" if the matching path element would be a Regex and contain
".*". This could cause issues with resource handling if the handler
mapping pattern was similar to `"/folder/file.*.extension"`.
This commit introduces a new `isLiteral()` method in the `PathElement`
abstract class that expresses whether the path element can be compared
as a String for path matching or if it requires a more elaborate
matching process.
Using this method for extracting the path within handler mapping avoids
relying on wildcard count or other properties.
See gh-29712
Fixes gh-29716
Prior to this commit, there was a bug in the implementation of
StandardRepeatableContainers.computeRepeatedAnnotationsMethod() which
has existed since Spring Framework 5.2 (when
StandardRepeatableContainers was introduced). Specifically,
StandardRepeatableContainers ignored any repeatable container
annotation if it declared attributes other than `value()`. However,
Java permits any number of attributes in a repeatable container
annotation.
In addition, the changes made in conjunction with gh-20279 made the bug
in StandardRepeatableContainers apparent when using the
getMergedRepeatableAnnotations() or findMergedRepeatableAnnotations()
method in AnnotatedElementUtils, resulting in regressions for the
behavior of those two methods.
This commit fixes the regressions and bug by altering the logic in
StandardRepeatableContainers.computeRepeatedAnnotationsMethod() so that
it explicitly looks for the `value()` method and ignores any other
methods declared in a repeatable container annotation candidate.
See gh-29685
Closes gh-29686
Prior to this commit, SpEL's ConstructorReference did not provide
support for arrays when generating a string representation of the
internal AST. For example, 'new String[3]' was represented as 'new
String()' instead of 'new String[3]'.
This commit introduces support for standard array construction and array
construction with initializers in ConstructorReference's toStringAST()
implementation.
Closes gh-29666
Prior to this commit, there were two bugs in the support for quotes
within String literals in SpEL expressions.
- Two double quotes ("") or two single quotes ('') were always replaced
with one double quote or one single quote, respectively, regardless
of which quote character was used to enclose the original String
literal. This resulted in the loss of one of the double quotes when
the String literal was enclosed in single quotes, and vice versa. For
example, 'x "" y' became 'x " y'.
- A single quote which was properly escaped in a String literal
enclosed within single quotes was not escaped in the AST string
representation of the expression. For example, 'x '' y' became 'x ' y'.
This commit fixes both of these related issues in StringLiteral and
overhauls the structure of ParsingTests.
Closes gh-29604
Closes gh-28356
In order to automate maintenance of copyright headers in our source
code (especially when merging PRs from external contributors), this
commit introduces an update_copyright_headers.sh script (tested on
mac OS) that will update the copyright headers of all Java, Kotlin,
and Groovy source files that have been added or modified this year
(or at least as far back as the git log history supports it).
For example, running this script currently outputs the following.
Updating copyright headers in Java, Kotlin, and Groovy source code for year 2022
warning: log for 'main' only goes back to Tue, 16 Aug 2022 16:24:55 +0200
When running on JDK 16+, we are not able to spy() on JDK types. To
address this, this commit stops using Mockito to spy on JDK I/O streams
(such as ByteArrayInputStream and ByteArrayOutputStream).
This commit fixes configuration and runtime issues with the Java 17 test
CI variant and removes the Java 11 one, now that Spring Framework 5.3.x
is in maintenance mode.
Prior to this commit, the addDefaultHttpMessageConverters() method in
WebMvcConfigurationSupport caught Throwable for SourceHttpMessageConverter
instantiation; whereas, the rest of the code base correctly catches Error
for SourceHttpMessageConverter instantiation (to handle errors such as
NoClassDefFoundError).
Throwable should not be caught since it can mask other categories of
failures (such as configuration errors).
This commit therefore switches to catching Error for SourceHttpMessageConverter
instantiation in WebMvcConfigurationSupport.
Closes gh-29537
SocketUtils was officially deprecated in 5.3.16 (gh-28052) and removed
in 6.0 M3 (gh-28054); however, there is still need for a subset of this
functionality in integration tests for testing scenarios in which it is
not possible for the system under test to select its own random port
(or rely on the operating system to provide an ephemeral port).
This commit therefore introduces a scaled down version in the
spring-test module called TestSocketUtils which supports retrieval of a
single TCP port.
See gh-29132
- Change "you ca" to "you can" in webflux.adoc
- English names can be used in "month" field instead of "day-of-month"
field in cron expressions in integration.adoc
Closes gh-29469
Prior to this commit, ternary and Elvis expressions enclosed in
parentheses (to account for operator precedence) were properly parsed
and evaluated; however, the corresponding toStringAST() implementations
did not enclose the results in parentheses. Consequently, the string
representation of the ASTs did not reflect the original semantics of
such expressions.
For example, given "(4 % 2 == 0 ? 1 : 0) * 10" as the expression to
parse and evaluate, the result of toStringAST() was previously
"(((4 % 2) == 0) ? 1 : 0 * 10)" instead of
"((((4 % 2) == 0) ? 1 : 0) * 10)", implying that 0 should be multiplied
by 10 instead of multiplying the result of the ternary expression by 10.
This commit addresses this by ensuring that SpEL ternary and Elvis
expressions are enclosed in parentheses in toStringAST().
Closes gh-29463
As a follow up to 332b25b680, this commit consistently avoids the use of
reflection for annotation attribute method invocations.
See gh-29301
Closes gh-29448
This commit makes sure that the current state of the PartGenerator
is able to handle an incoming buffer, possibly requested because of
a request coming from the subscription. All states accept new buffers
except the WritingFileState.
Closes gh-29227
LeakAwareDataBufferFactory#checkForLeaks automatically waits up to 5
sec for buffers to be released, which could be used as a way of
awaiting on some async logic to complete, and as long as buffers are
released, it shouldn't be long. However, the leak test in
LeakAwareDataBufferFactoryTests actually expects to find a leak, and
always ends up waiting the full 5 seconds.
This change, makes the wait configurable, with the no-arg method
using 0 (no waiting). AbstractLeakCheckingTests uses 1 second by
default since ResourceRegionEncoderTests did fail locally. If more
tests need this, we can adjust the settings.
Conditional requests using "If-Unmodified-Since" headers are generally
used as precondition checks for state-changing methods (POST, PUT,
DELETE). See https://datatracker.ietf.org/doc/html/rfc7232#section-3.4
The spec also allows for idempotent methods like GET and HEAD.
Prior to this commit, the "If-Unmodified-Since" processing done in
`checkNotModified` (see `ServletWebRequest` and
`DefaultServerWebExchange`) would only focus on the state changing
methods and not take into account the safe methods. For those cases, the
"ETag" and "Last-Modified" would be missing from the response.
This commit ensures that such headers are added as expected in these
cases.
Fixes gh-29362
At present, creating LoggingCacheErrorHandler with custom logger requires use of Commons Logging API, as the appropriate constructor expects org.apache.commons.logging.Log instance. As Commons Logging is rarely the logging framework of choice in applications these days, interaction with its API might not be desirable.
This commit adds LoggingCacheErrorHandler constructor that accepts logger name and thus avoids leaking out any details about the underlying logging framework.
Prior to this commit, searches for non-public repeatable annotations
failed with error messages similar to the following, since the
repeatable annotation's container's `value()` method could not be
invoked via reflection.
JDK 8:
java.lang.IllegalAccessError: tried to access class
org.springframework.core.annotation.NestedRepeatableAnnotationsTests$A
from class com.sun.proxy.$Proxy12
JDK 17:
java.lang.IllegalAccessError: failed to access class
org.springframework.core.annotation.NestedRepeatableAnnotationsTests$A
from class jdk.proxy2.$Proxy12
(org.springframework.core.annotation.NestedRepeatableAnnotationsTests$A
is in unnamed module of loader 'app'; jdk.proxy2.$Proxy12 is in module
jdk.proxy2 of loader 'app')
This commit makes it possible to search for non-public repeatable
annotations by first attempting to invoke the repeatable annotation's
container's `value()` method via the container's InvocationHandler (if
the container is a JDK dynamic proxy) and then falling back to
reflection for the method invocation if an error occurs (such as a
SecurityException).
Closes gh-29301
This commit is a follow up to 828f74f71a
and applies to same fix for getMergedRepeatableAnnotations().
See the previous commit for details.
Closes gh-20279
Prior to this commit, the findMergedRepeatableAnnotations() methods in
AnnotatedElementUtils failed to find repeatable annotations declared
on other repeatable annotations (i.e., when one repeatable annotation
type was used as a meta-annotation on a different repeatable annotation
type).
The reason is that
findMergedRepeatableAnnotations(element, annotationType, containerType)
always used RepeatableContainers.of(annotationType, containerType) to
create a RepeatableContainers instance, even if the supplied
containerType was null. Doing so restricts the search to supporting
only repeatable annotations whose container is the supplied
containerType and prevents the search from finding repeatable
annotations declared as meta-annotations on other types of repeatable
annotations.
Note, however, that direct use of the MergedAnnotations API already
supported finding nested repeatable annotations when using
RepeatableContainers.standardRepeatables() or
RepeatableContainers.of(...).and(...).and(...). The latter composes
support for multiple repeatable annotation types and their containers.
This commit addresses the issue for findMergedRepeatableAnnotations()
when the containerType is null or not provided.
However, findMergedRepeatableAnnotations(element, annotationType, containerType)
still suffers from the aforementioned limitation, and the Javadoc has
been updated to make that clear.
Closes gh-20279
Prior to this commit, ExchangeResult.assertWithDiagnostics() threw an
IllegalArgumentException for a custom HTTP status code since toString()
invoked getStatus() without a try-catch block.
This commit addresses this issue by introducing a formatStatus() method
that defensively formats the response status, initially trying to
format the HttpStatus and falling back to formatting the raw integer
status code.
Closes gh-29283
This commit introduces tests which serve as "regression tests" for the
behavior of PathMatchingResourcePatternResolver in Spring Framework
5.3.x with regard to URL-encoding and Unicode normalization of resource
paths.
Specifically, the new tests demonstrate that resource paths do NOT need
to be decoded or normalized in 5.3.x.
See gh-29243
Prior to this commit, `ServletContextResource` could rely on
`ServletContext#getRealPath` to check whether a resource exists.
This behavior is not enforced on some Servlet containers, as this method
is only meant to translate virtual paths to real paths, but not
necessarily check for the existence of the file.
See https://bz.apache.org/bugzilla/show_bug.cgi?id=55837#c3 for a
rationale of this behavior in Tomcat.
This commit enforces an additional check, resolving the path as a `File`
and checking that is exists and is a file.
Closes gh-26707
Previously, if `@Order` is specified on a `@Bean` method, and the
candidate bean is defined in a parent context, its order wasn't taken
into account when retrieving the bean from a child context.
This commit makes sure the metadata of a bean is taken into
consideration in all cases.
Closes gh-29105
This commit ensures that when using `sendRedirect`, the response wrapper
behaves correctly with regards to the Servlet specification:
1. reset the response buffer to clear any partially written response
2. set the expected response HTTP headers
3. flush the buffer to commit the response
Closes gh-29050
This commit fixes Kotlin Serialization converter
registration logic in RestTemplate,
AbstractMessageBrokerConfiguration and
AllEncompassingFormHttpMessageConverter classes
to be similar to the one in
WebMvcConfigurationSupport.
Closes gh-29008
Since SynthesizedAnnotation will be deprecated (and potentially
completely removed) in Spring Framework 6.0, this commit introduces
AnnotationUtils.isSynthesizedAnnotation(Annotation) in 5.3.x to allow
people to migrate away from relying on SynthesizedAnnotation.
Closes gh-29054
This commit fixes a race condition in PartGenerator, used by
DefaultPartHttpMessageReader. The condition can occur when a
completion signal comes in, and the state is changed to IdleFileState
at the same time.
Closes gh-28963
Prior to this commit, MockServerContainerContextCustomizerFactory did
not find @WebAppConfiguration on an enclosing class and therefore
failed to create a MockServerContainerContextCustomizer for a @Nested
test class.
This commit addresses this by using TestContextAnnotationUtils to
determine if the test class is "annotated" with @WebAppConfiguration.
Closes gh-29037
Prior to this commit it was possible to configure the
DefaultListableBeanFactory used by the GenericWebApplicationContext
created by AbstractWebGenericContextLoader, but it was not possible to
completely replace the bean factory.
This commit introduces a new createContext() factory method in
AbstractWebGenericContextLoader which indirectly allows subclasses to
supply a custom DefaultListableBeanFactory implementation to the
GenericWebApplicationContext.
See gh-25600
Closes gh-28983
NestedIOException has been removed in Spring Framework 6 and this commit
marks it as deprecated in 5.x. Users that were relying on this exception
should use IOException directly.
Closes gh-28929
Prior to this commit, the `AbstractFileResolvingResource` would
provide a default implementation for `customizeConnection` which only
sets the HTTP request method as "HEAD".
While this is consistent with its usage within that class (in
`exists()`, `contentLength()` or `lastModified()`), this is not opened
for general usage by sub-classes.
`UrlResource` is an example of that, where its `getInputStream()` method
does not call this customization method.
This not only prevents implementations from calling
`customizeConnection` in various cases, but it also misleads developers
as they might think that customizations will be applied automatically.
This commit ensures that `customizeConnection` is called in all relevant
places and that the configuration of the HTTP method is instead done in
each method as it is use case specific.
Fixes gh-28909
Not all HttpHeaders implementations are serializable. This commit
ensures that WebClientRequestException and WebClientResponseException
are serializable, by copying any non-serializable HttpHeaders into a
new, serializable, instance.
Closes gh-28321
Not all HttpHeaders implementations are serializable. This commit
ensures that WebClientRequestException and WebClientResponseException
are serializable, by copying any non-serializable HttpHeaders into a
new, serializable, instance.
Closes gh-28321
SockJsServiceRegistration#setSupressCors name contains a typo. It is
now deprecated in favor of a correctly spelled method, setSuppressCors.
See gh-28853
This commit correctly identifies MaxUploadSizeExceededException in
StandardMultipartHttpServletRequest by converting keywords in the
exception message to lowercase before checking for their presence, for
compatibility with Jetty 9.4.x.
Closes gh-28759
Prior to this commit, tests in these two classes intermittently failed
with errors similar to the following, due to concurrent modification
of shared files.
expected:
"<input type="text" id="name" name="name" value="Darren" >"
but was:
"<input type="text" id="name" name="name" value="Darren" >
"hidden"/>"
This commit fixes this by creating a new temporary folder for each test
method invocation.
Prior to this commit, a DataSize input string could not be parsed if it
contained any whitespace.
With this commit, a DataSize input string can contain leading, trailing,
or 'in between' whitespace. For example, the following will be parsed
to the same DataSize value.
- "1024B"
- "1024 B"
- " 1024B "
- " 1024 B "
Closes gh-28643
The previous change to the tests resulted in a failure on Windows when
using the DefaultResourceLoader by expecting an exception when no
exception is thrown.
This commit narrows the scope of the if-clause to expect an exception
only when using the FileSystemResourceLoader on Windows.
See gh-28703, gh-28746
The tests introduced in commit 9868c28c73 pass on Mac OS and Linux but
fail on Microsoft Windows.
This commit updates the tests so that they pass on MS Windows as well.
See gh-28703
Closes gh-28746
Prior to this commit, if a cookie was added to MockHttpServletResponse,
the comment attribute was not included in the generated Set-Cookie
header. In addition, MockCookie.parse(String) did not support the
Comment attribute.
This commit addresses both of these issues.
Closes gh-28730
Commit d6768ccc18 introduced a regression in the support for merging
annotation attributes in a multi-level annotation hierarchy.
This commit addresses that issue by ensuring that a merged annotation
is once again synthesized if a meta-annotation in the annotation
hierarchy declares attributes that override attributes in the target
annotation.
Closes gh-28716
When the ProtocolResolver SPI was introduced in Spring Framework 4.3,
support for protocol resolvers was added in DefaultResourceLoader's
getResource() implementation; however, GenericApplicationContext's
overridden getResource() implementation was not updated accordingly.
Prior to this commit, if a GenericApplicationContext was configured
with a custom ResourceLoader, registered protocol resolvers were
ignored.
This commit ensures that protocol resolvers are honored in
GenericApplicationContext even if a custom ResourceLoader is used.
Closes gh-28703
Prior to this commit, meta-annotations were unnecessarily synthesized
when attempting to synthesize a MergedAnnotation retrieved via the
MergedAnnotations.from(AnnotatedElement, ...).get(<annotationType>) API.
This is a regression in our merged annotation support that was
introduced when the MergedAnnotations API replaced our previous support.
This commit fixes this by revising the logic in TypeMappedAnnotation's
createSynthesizedAnnotation() method so that a meta-annotation is
returned unmodified if it is not synthesizable.
This commit also updates BootstrapUtilsTests, since @BootstrapWith
should never have been synthesized, and Class#getCanonicalName() is
only used in the toString() implementation of an annotation synthesized
by Spring or normal annotations on Java 19+ (see
https://bugs.openjdk.org/browse/JDK-8281462).
Closes gh-28704
Align IllegalStateException with SQLException handling and propagate
the original exception.
See gh-28669
Co-authored-by: Christoph Mies <chr.mi@web.de>
Since LoggingCacheErrorHandler was only recently introduced in 5.3.16,
we have decided to completely revise its internals (protected API) in
5.3.x while retaining the current public API.
Specifically, this commit:
- introduces protected getLogger() and isLogStackTraces() methods to
improve extensibility
- revises logCacheError() to accept a Supplier<String> for lazy
resolution of error messages
Closes gh-28672
See gh-28670, gh-28648
At present, creating a LoggingCacheErrorHandler that logs stack traces
also requires supplying the logger to be used. This might be
inconvenient for some users, as it requires usage of the Commons
Logging API.
This commit simplifies creation of such as LoggingCacheErrorHandler
instance by adding a constructor that only accepts a boolean flag
indicating whether to log stack traces.
Closes gh-28670
Update test detecting RouterFunction beans in parent contexts to use
different bean names and avoid shadowing. Changed the fix accordingly
given that BeanProvider does detect beans in parent contexts.
See gh-28595
Prior to this commit, ObjectToObjectConverter considered the return
type of non-static `to[targetType.simpleName]()` methods but did not
consider the return type of static `valueOf(sourceType)`,
`of(sourceType)`, and `from(sourceType)` methods.
This led to scenarios in which `canConvert()` returned `true`, but a
subsequent `convert()` invocation resulted in a
ConverterNotFoundException, which violates the contract of the
converter.
This commit addresses this issue by taking into account the return type
of a static valueOf/of/from factory method when determining if the
ObjectToObjectConverter supports a particular conversion. Whereas the
existing check in `determineToMethod()` ensures that the method return
type is assignable to the `targetType`, the new check in
`determineFactoryMethod()` leniently ensures that the method return
type and `targetType` are "related" (i.e., reside in the same type
hierarchy).
Closes gh-28609
We use Grafana to monitor our app via Spring's JMX exporter, and we
think it could be interesting to have at least the current queue size
for this purpose since the queue size directly affects the app memory
load. Having the queue capacity seems also interesting to set up
triggers whose values are calculated based on the maximum capacity of
the queue.
This commit introduces new getCurrentQueueSize() and getQueueCapacity()
methods in ThreadPoolTaskExecutor.
See gh-28583
To avoid unnecessary eager initialization of DataSize.PATTERN, this
commit initializes it lazily in the first invocation of DataSize.parse
by moving PATTERN to a private static nested class.
Closes gh-28560
Prior to this commit, getPort() in HierarchicalUriComponents threw a
NumberFormatException for an invalid port supplied as a String, which
was inconsistent with exception handling elsewhere in the class as well
as within the same method.
This commit introduces a try-catch block in getPort() to consistently
throw IllegalStateExceptions for ports that cannot be parsed.
Closes gh-28521
Decoding is required for non-UrlResource when the HandlerMapping is
not expected to decode the path. Encoding is the opposite.
This commit ensures correct determination of whether the HandlerMapping
is expected to have decoded the path or not that in turn depends on
whether PathPattern or PathMatcher is in use.
Closes gh-27791
A static nested class does not keep an implicit reference to its
enclosing instance.
This prevents a common cause of memory leaks and uses less memory per
instance of the class.
Closes gh-28433
Prior to this commit, the `name` attribute in @ModelAttribute was not
supported when using WebFlux. This is because MethodParameter was used
instead of SynthesizingMethodParameter when retrieving the
@ModelAttribute annotation. In other words, @AliasFor was not honored
because the annotation was not synthesized. Consequently, only the
`value` attribute was supported in WebFlux when specifying a custom name
via @ModelAttribute.
This commit fixes this by using SynthesizingMethodParameter to retrieve
the @ModelAttribute annotation.
Closes gh-28423
This commit makes sure that TomcatServerHttpRequest::readFromInputStream
follows the same contract as the method it overrides, and returns
AbstractListenerReadPublisher.EMPTY_BUFFER when 0 bytes are read.
See gh-28241
If we read 0 bytes, e.g. chunked encoding markup read but not the
actual data within it, don't stop reading since the server may or
may not consider it necessary to call onDataAvailable again.
Instead, we keep on reading, and although isReady likely returns
false on the next iteration, it eliminates ambiguity and ensures
the server will call onDataAvailable when more data arrives.
Closes gh-28241
With a Java 8 baseline in place for quite some time now, it no longer
makes sense to refer to features such as annotations as "Java 5
annotations".
This commit also removes old `Tiger*Tests` classes, thereby avoiding
duplicate execution of various tests.
This commit adds a warning to the Javadoc for the
TYPE_HIERARCHY_AND_ENCLOSING_CLASSES search strategy in
MergedAnnotations with regard to the scope of the search
algorithm.
See gh-28079
Since Spring Framework 5.3, BeanUtils.copyProperties() honors generics
in the source and target property types (see gh-24187); however, this
refinement of the contract was not properly documented prior to this
commit. In addition, the refinement can be a breaking change for users
who were relying on the previous unreliable behavior.
This commit therefore clarifies the behavior for generics support in
BeanUtils.copyProperties() and introduces a table of example matches
and mismatches when generics are involved.
Closes gh-27259
This commit makes sure that the response returned by coroutine handler
methods that return ResponseEntity<Flux> is unwrapped correctly.
Closes gh-27809
Attempting to create a large array in a SpEL expression can result in
an OutOfMemoryError. Although the JVM recovers from that, the error
message is not very helpful to the user.
This commit improves the diagnostics in SpEL for large array creation
by throwing a SpelEvaluationException with a meaningful error message
in order to improve diagnostics for the user.
Closes gh-28145
This commit improves the documentation for test execution events,
especially with regard to the fact that, by default, a
BeforeTestClassEvent is not published for the first test class using a
particular ApplicationContext.
This commit also introduces tests that verify the default behavior and
the ability to change the default behavior with a custom
TestExecutionListener that eagerly loads the context.
Closes gh-27757
This commit introduces Javadoc to explain the difference between
init/destroy method names when such methods are private, namely that a
private method is registered via its qualified method name; whereas, a
non-private method is registered via its simple name.
See gh-28083
Prior to this commit, `AsyncRestTemplate` would log errors (including
simple 404s) with WARN level. Such errors are quite common and should
not clutter logs.
This commit aligns the logging strategy with RestTemplate, using the
DEBUG level for such cases.
Fixes gh-28049
Before this commit, CronField.Type::rollForward added temporal units
to reach the higher order field. This caused issues with DST, where
the added amount of hours was either too small or too large.
This commit refactors the implementation so that it now adds one to the
higher order field, and reset the current field to the minimum value.
Closes gh-28095
The TYPE_HIERARCHY_AND_ENCLOSING_CLASSES search strategy for
MergedAnnotations was originally introduced to support @Nested test
classes in JUnit Jupiter (see #23378).
However, while implementing #19930, we determined that the
TYPE_HIERARCHY_AND_ENCLOSING_CLASSES search strategy unfortunately
could not be used since it does not allow the user to control when to
recurse up the enclosing class hierarchy. For example, this search
strategy will automatically search on enclosing classes for static
nested classes as well as for inner classes, when the user probably
only wants one such category of "enclosing class" to be searched.
Consequently, TestContextAnnotationUtils was introduced in the Spring
TestContext Framework to address the shortcomings of the
TYPE_HIERARCHY_AND_ENCLOSING_CLASSES search strategy.
Since this search strategy is unlikely to be useful to general users,
the team has decided to deprecate this search strategy in Spring
Framework 5.3.x and remove it in 6.0.
Closes gh-28079
Prior to this commit, SpEL was able to recover from an error that
occurred while running a CompiledExpression; however, SpEL was not able
to recover from an error that occurred while compiling the expression
(such as a java.lang.VerifyError). The latter can occur when multiple
threads concurrently change types involved in the expression, such as
the concrete type of a custom variable registered via
EvaluationContext.setVariable(...), which can result in SpEL generating
invalid bytecode.
This commit addresses this issue by catching exceptions thrown while
compiling an expression and updating the `failedAttempts` and
`interpretedCount` counters accordingly. If an exception is caught
while operating in SpelCompilerMode.IMMEDIATE mode, the exception will
be propagated via a SpelEvaluationException with a new
SpelMessage.EXCEPTION_COMPILING_EXPRESSION error category.
Closes gh-28043
Update the pluginManagement repositories used by Grade to include
`mavenCentral()` since `gradlePluginPortal()` has been suffering
from timeouts recently.
Prior to this commit, it was not clear that a configured base URI would
not be applied when invoking uri(URI).
This commit adds a note to the Javadoc to clarify that behavior.
Closes gh-28058
SocketUtils was introduced in Spring Framework 4.0, primarily to assist
in writing integration tests which start an external server on an
available random port. However, these utilities make no guarantee about
the subsequent availability of a given port and are therefore
unreliable. Instead of using SocketUtils to find an available local
port for a server, it is recommended that users rely on a server's
ability to start on a random port that it selects or is assigned by the
operating system. To interact with that server, the user should query
the server for the port it is currently using.
SocketUtils is now deprecated in 5.3.16 and will be removed in 6.0.
Closes gh-28052
In 3ec612aaf8, I accidentally removed tests that verified support for
non-synthesizable merged annotations for recursive annotations in
Kotlin.
This commit reinstates those non-synthesizable tests while retaining
the synthesizable tests.
This commit upgrades the CI pipeline with the following:
* replace JDK16 with JDK17 as build variant
* upgrade all JDK versions
* replace docker-image with registry-image resource for CI image
Although Java does not allow the definition of recursive annotations,
Kotlin does, and prior to this commit an attempt to synthesize a
merged annotation using the MergedAnnotation API resulted in a
StackOverflowError if there was a recursive cycle in the annotation
definitions.
This commit addresses this issue by tracking which annotations have
already been visited and short circuits the recursive algorithm if a
cycle is detected.
Closes gh-28012
Although the initial report in gh-28015 only covered inconsistencies
for arrays and strings in the toString() implementations for
annotations between the JDK (after Java 9) and Spring, it has since
come to our attention that there was further room for improvement.
This commit therefore addresses the following in toString() output for
synthesized annotations.
- characters are now wrapped in single quotes.
- bytes are now properly formatted as "(byte) 0x##".
- long, float, and double values are now appended with "L", "f", and
"d", respectively. The use of lowercase for "f" and "d" is solely to
align with the choice made by the JDK team.
However, this commit does not address the following issues which we may
choose to address at a later point in time.
- non-ASCII, non-visible, and non-printable characters within a
character or String literal are not escaped.
- formatting for float and double values does not take into account
whether a value is not a number (NaN) or infinite.
Closes gh-28015
Since the introduction of synthesized annotation support in Spring
Framework 4.2 (a.k.a., merged annotations), the toString()
implementation attempted to align with the formatting used by the JDK
itself. However, Class annotation attributes were formatted using
Class#getName in Spring; whereas, the JDK used Class#toString up until
JDK 9.
In addition, JDK 9 introduced new formatting for toString() for
annotations, apparently intended to align with the syntax used in the
source code declaration of the annotation. However, JDK 9+ formats enum
annotation attributes using Enum#toString instead of Enum#name, which
can lead to issues if toString() is overridden in an enum.
This commit updates the formatting used for synthesized annotations by
ensuring that toString() generates a string that is compatible with the
syntax of the originating source code, going beyond the changes made in
JDK 9 by using Enum#name instead of Enum#toString.
Closes gh-28015
Prior to this commit, WebTestClient only supported "lenient" comparison
of the expected JSON body.
This commit introduces an overloaded variant of `json()` in the
BodyContentSpec that accepts an additional boolean flag to specify
whether a "strict" comparison should be performed.
This new feature is analogous to the existing support in MockMvc.
Closes gh-27993
Prior to this commit, if AOP proxy generation was configured with
proxyTargetClass=true (which is the default behavior in recent versions
of Spring Boot), beans implemented as lambda expressions or method
references could not be proxied with CGLIB on Java 16 or higher without
specifying `--add-opens java.base/java.lang=ALL-UNNAMED`.
This commit addresses this shortcoming by ensuring that beans
implemented as lambda expressions or method references are always
proxied using a JDK dynamic proxy even if proxyTargetClass=true.
Closes gh-27971
Prior to this commit, the QuartzCronField::weekdayNearestTo would elapse
until the next month before checking if the current day matched.
After this commit, the current day is checked before we elapse until
the next month.
Closes gh-27966
In a small minority of cases, the multipart boundary can spread across
three incoming buffers.
Prior to this commit, MultipartParser.BodyState only supported two
buffers. If the boundary is spread across three buffers, the first
buffer of the three is sent as a whole, even though it contains the
first bytes of the boundary.
This commit fixes this bug, by enqueuing all prior buffers in a queue,
and emitting the ones that cannot contain boundary bytes.
Closes gh-27939
Prior to this commit, the USER_DECLARED_METHODS MethodFilter in
ReflectionUtils did not actually filter methods declared in
java.lang.Object as stated in its Javadoc.
Consequently, if ReflectionUtils.doWithMethods was invoked with
USER_DECLARED_METHODS and Object.class as the class to introspect, all
non-bridge non-synthetic methods declared in java.lang.Object were
passed to the supplied MethodCallback, which breaks the contract of
USER_DECLARED_METHODS.
In addition, if USER_DECLARED_METHODS was composed with a custom
MethodFilter using `USER_DECLARED_METHODS.and(<custom MethodFilter>)`,
that composed method filter allowed all non-bridge non-synthetic
methods declared in java.lang.Object to be passed to the supplied
MethodCallback, which also breaks the contract of
USER_DECLARED_METHODS. This behavior resulted in regressions in code
that had previously used USER_DECLARED_METHODS by itself and then began
using USER_DECLARED_METHODS in a composed filter. For example, since
commit c419ea7ba7 ReflectiveAspectJAdvisorFactory has incorrectly
processed methods in java.lang.Object as candidates for advice methods.
This commit fixes this bug and associated regressions by ensuring that
USER_DECLARED_METHODS actually filters methods declared in
java.lang.Object. In addition, ReflectionUtils.doWithMethods now aborts
its search algorithm early if invoked with the USER_DECLARED_METHODS
filter and Object.class as the class to introspect.
Closes gh-27970
Prior to this commit, we only (indirectly) configured external Javadoc
links for types in the javax.annotation package for JSR 250, since
those types are part of Java 8 SE. However, an external Javadoc link
for types from JSR 305 was not configured.
To address this issue, this commit now configures an external Javadoc
link for JSR 305 types. However, the external Javadoc link for JSR 305
must be configured last to ensure that types from JSR 250 (such as
@PostConstruct) are still supported. This is due to the fact that JSR
250 and JSR 305 both define types in javax.annotation, which results in
a split package, and the javadoc tool does not support split packages
across multiple external Javadoc sites. Instead, the Javadoc tool
iterates over all external links, and the first external site that
claims to support a given package (via the package-list file) wins.
This means:
- Javadoc for JSR 250 annotations is fully supported.
- Javadoc for JSR 305 annotations in the javax.annotation package will
continue to result in a 404 (page not found) error.
- Javadoc for JSR 305 annotations in the javax.annotation.meta package
is fully supported.
For Spring Framework 6.0, the Javadoc for JSR 250 types in
jakarta.annotation package is served from the JBoss Application Server
Javadoc site instead of from Oracle's Java SE documentation site, since
JSR 250 annotations are no longer included in Java SE.
Closes gh-27904
Prior to this commit, if a PropertySourcesPlaceholderConfigurer bean
was configured with its ignoreUnresolvablePlaceholders flag set to
true, unresolvable placeholders in an @Value annotation were not
ignored, resulting in a BeanCreationException for the bean using @Value.
For example, given a property declared as `my.app.var = ${var}` without
a corresponding `var` property declared, an attempt to resolve
`@Value("${my.app.var}")` resulted in the following exception.
java.lang.IllegalArgumentException: Could not resolve placeholder 'var' in value "${var}"
This commit fixes this by modifying
PropertySourcesPlaceholderConfigurer's postProcessBeanFactory(...)
method so that a local PropertyResolver is created if the
ignoreUnresolvablePlaceholders flag is set to true. The local
PropertyResolver then enforces that flag, since the Environment in the
ApplicationContext is most likely not configured with
ignoreUnresolvablePlaceholders set to true.
Closes gh-27947
Commit 6316a35 introduced a regression for property names starting with
multiple uppercase letters (such as setEMail(...)).
This commit fixes that regression and includes an additional test to
cover this case.
See gh-27929
Closes gh-27941
Instead of simply returning prematurely and allowing the tests to be
marked as SUCCESS, this commit uses a failed assumption to abort the
the trasferTo tests for Undertow, resulting in the parameterized test
invocation properly being marked as ABORTED.
See gh-25310
Prior to this commit, XmlValidationModeDetector did not properly parse
all categories of comments (described below). When such categories of
comments were encountered XmlValidationModeDetector may have
incorrectly detected that an XML file used a DTD when it used an XSD,
or vice versa.
This commit revises the parsing algorithm in XmlValidationModeDetector
so that multi-line comments and multiple comments on a single line are
properly recognized.
Specifically, with this commit the following categories of comments are
now handled properly.
- Multiple comments on a single line
- Multi-line comment: beginning on one line and then ending on another
line with an additional comment following on that same line.
- Multi-line comment: beginning at the end of XML content on one line
and then spanning multiple lines.
Closes gh-27915
Prior to this commit, the PrintingResultHandler in MockMvc -- typically
invoked via .andDo(print()) -- printed an `application/json` response
body using the default encoding (ISO-8859-1), which resulted in UTF-8
characters being garbled.
Since an `application/json` response is implicitly encoded using UTF-8,
the PrintingResultHandler now infers UTF-8 encoding for such response
bodies.
Closes gh-27926
The failing test is for Apache HttpComponents where we cannot apply the
Content-Length together with other headers, and must pass it instead
explicitly to ReactiveEntityProducer when writing at which point it gets
set in the native headers.
Closes gh-27768
NettyHeadersAdapter::putAll uses HttpHeaders::add, which does not
overwrite existing headers. putAll should use HttpHeaders::set instead,
just like NettyHeadersAdapter::put does.
Closes gh-27887
Prior to this commit, the error message generated for a mismatched
number of generics did not include the information about the class in
question.
This commit improves the error message by providing more context,
specifically the result of invoking toGenericString() on the class.
For example, instead of throwing an IllegalArgumentException with the
error message "Mismatched number of generics specified", the error
message would now be "Mismatched number of generics specified for
public abstract interface java.util.Map<K,V>".
Closes gh-27847
@hpoettker made me aware of the ModeEnum in H2 that allows the
parameterized test to be simplified, which was the primary impetus for
this commit.
See gh-27870
The test case is intended to be for the method 'withRootObject()', but
actually it's copied from the previous test method that does not use
'withRootObject()'.
This commit fixes the propertyReadWriteWithRootObject() test method in
PropertyAccessTests.
Closes gh-27905
Commit ed4e2289cd introduced support for H2 2.0.x but did not upgrade
the H2 dependency.
This commit upgrades the H2 dependency to version 2.0.206 but also
adds an explicit test dependency on version 1.4.200 in spring-r2dbc,
since r2dbc-h2 does not yet support H2 2.0.x.
Once https://github.com/r2dbc/r2dbc-h2/pull/204 has been included in a
released version of r2dbc-h2 we will be able to upgrade spring-r2dbc's
test dependency on the H2 database to 2.0.x as well.
See gh-27870
See gh-27902
Prior to this commit, H2SequenceMaxValueIncrementer only supported H2
database 1.4.
This commit updates H2SequenceMaxValueIncrementer's getSequenceQuery()
method so that the syntax used supports version 1.4 and 2.0 of the H2
database.
This commit also updates several test schemas so that they work with H2
1.4 and 2.0 as well as HSQL.
Closes gh-27870
The EntityManager interface does not implement AutoCloseable until
JPA 3.1.
This commit therefore partially reverts 189e1afc6e so that the
example code compiles with the supported JPA version.
See gh-22269
Closes gh-27886
Where unfeasible, this commit adds inline comments to explain why
try-with-resources must not be used in certain scenarios. The purpose
of the comments is to avoid accidental conversion to try-with-resources
at a later date.
Closes gh-27823
This helps to reduce noise in the "Problems" view by not displaying
warnings resulting from @SuppressWarnings tokens that Eclipse does not
understand -- for example, tokens supported by IntelliJ IDEA or other
tools.
Although this commit only applies to test classes, it serves to reduce
the noise when searching for undesirable usage of StringBuffer in
production code.
The getBeanFactory() method has been obsolete for more than 13 years
since it was superseded by the getRegistry() method in the
BeanDefinitionReader interface.
Closes gh-27875
This commit adds default methods to CachingConfigurer and
JCacheConfigurer and removes the reference to their respective support
classes as they are now irrelevant.
Closes gh-27811
Prior to this commit, if a single null value was passed to a method with
a varargs array of type java.util.Optional, that null value was passed
unmodified. On the contrary, a null passed with additional values to
such a method resulted in the null being converted to Optional.empty().
This commit ensures that a single null value is also converted to
Optional.empty() for such SpEL expressions.
Closes gh-27795
A regression was introduced in gh-27582. Specifically, when null is
supplied as the single argument for a varargs parameter in a method or
function in a SpEL expression, ReflectionHelper currently throws a
NullPointerException instead of leaving the null value unchanged.
This commit fixes this regression.
Closes gh-27719
This commit makes it possible to customize 404 responses generated by
RouterFunctionWebHandler, by throwing an ResponseStatusException
instead of returning a standard 404 response.
See gh-25358
Prior to this commit, ServerResponse headers would only be written if
there were no existing headers with the same name, thus making it
impossible to overwrite existing headers.
With the changes in this commit, headers are always written.
Closes gh-27741
* pr/2030:
Polish "Clarify behaviour of AnnotationBeanNameGenerator with acronyms"
Clarify behaviour of AnnotationBeanNameGenerator with acronyms
Closes gh-2030
Name transformation is delegated to Introspector#decapitalize, which
states "but in the (unusual) special case when there is more than one
character and both the first and second characters are upper case, we
leave it alone.". This commit clarifies this behavior.
See gh-2030
The default documentation does not mention xxx*yyy pattern matching,
which is, however, supported by PatternMatchUtils. Such a pattern
can be useful for matching nested properties in all elements of a
collection, e.g. property[*].nestedProperty.
See gh-699
This commit ensures that only HTML references of length <
MAX_REFERENCE_SIZE are considered as potential references. This check is
possible because reference longer than 10 digits are out of bounds for
Integers.
Closes gh-1249
This commit changes DefaultClientResponse::createException to use
the ByteArrayDecoder, instead of converting to DataBuffers and
turning these into a byte array.
Closes gh-27666
This commit fixes a bug in the DefaultPartHttpMessageReader, in the
check for exceeding the maximum header size. Before this commit, the
entire buffer size was considered, thus triggering an exception even
though the max header limit was not exceeded. After this commit, we only
consider the size up until the end-of-header mark (CRLFCRLF).
Furthermore, this commit increases the default maximum header size to
10k, the same default as Commons File upload.
Closes gh-27612
Prior to this commit, Spring's SchedulerFactoryBean always set the
"org.quartz.jobStore.class" property to LocalDataSourceJobStore even if
the user had already specified a custom JobStore implementation via the
Quartz properties file or Properties object, thereby effectively
ignoring the user configuration.
This commit addresses this by configuring Quartz to use Spring's
LocalDataSourceJobStore only if a JobStore has not already been
specified via user configuration.
Closes gh-27560
Prior to this commit, UndertowHeadersAdapter's remove() method violated
the java.util.Map contract by always returning null.
This commit fixes this by returning the previous list stored under the
specified key, and otherwise returning null if no previous value was
present.
Closes gh-27592
Prior to this commit, if a SpEL expression invoked a method or
registered function that declares a String varargs argument, there were
sometimes issues with converting the input arguments into the varargs
array argument. Specifically, if the expression supplied a single
String argument containing a comma for the varargs (such as "a,b"),
SpEL's ReflectionHelper.convertArguments() method incorrectly converted
that single String to an array via the ConversionService, which
indirectly converted that String using the StringToArrayConverter,
which converts a comma-delimited String to an array. Thus, "a,b"
effectively got converted to a two-dimensional array ["a", "b"] instead
of simply ["a,b"].
This commit fixes this bug by avoiding use of the TypeConverter and
ConversionService for single arguments supplied as varargs when the
single argument's type matches the varargs array component type.
Closes gh-27582
Prior to this commit, third parties using @ComponentScan's @Filter
annotation had to implement their own parsing for @Filter
AnnotationAttributes as well as instantiation of the corresponding
TypeFilters. In such cases the various *Aware callbacks
(BeanFactoryAware, EnvironmentAware, etc.) should also be supported.
This commit therefore extracts a new public TypeFilterUtils class from
ComponentScanAnnotationParser so that third parties can benefit from
consistent TypeFilter creation from @ComponentScan @Filter annotations.
Closes gh-27553
The fix made for gh-27488 resulted in a change of the default order
of codecs. This commit reverts these changes, so that the previous
order is restored.
Closes gh-27573
This commit fixes the Javadoc in all queryForObject(...) methods in
JdbcOperations and NamedParameterJdbcOperations regarding what kinds of
exceptions are thrown under which conditions.
Closes gh-27559
Prior to this commit, DatabasePopulatorUtils.execute(...) did not
perform a commit for the current Connection. This works for most use
cases; however, when DatabasePopulatorUtils is used to execute
initialization scripts without a managed transaction -- for example,
via a DataSourceInitializer configured as a bean in the
ApplicationContext or via Spring Boot configuration in
application.properties -- if the underlying database is configured with
auto-commit=false, the results of executing the SQL scripts are not
committed to the database which can lead to data being silently lost.
This commit addresses this issue by committing the Connection for the
supplied DataSource if the connection is not configured for auto-commit
and is not transactional. Existing use cases running with a managed
transaction should therefore not be affected by this change.
Closes gh-27008
ResponseEntityResultHandler nests correctly, only once for the ResponseEntity,
when there is a Mono adapted from a Kotlin Continuation.
Closes gh-27292
In our application we use XML context and <cache:annotation-driven />
declaration. Also we disable bean definition duplication by setting
GenericApplicationContext.setAllowBeanDefinitionOverriding(false) in an
ApplicationContextInitializer. This combination leads to a
BeanDefinitionOverrideException because the
DefaultJCacheOperationSource bean is registered twice.
- once for: parserContext.getReaderContext().registerWithGeneratedName(sourceDef);
- once for: parserContext.registerBeanComponent(new BeanComponentDefinition(sourceDef, sourceName));
This commit refactors JCacheCachingConfigurer.registerCacheAspect(...)
so that the JCacheOperationSource bean is registered only once.
Closes gh-27499
Prior to this commit, the default CacheAwareContextLoaderDelegate could
be configured by extending AbstractTestContextBootstrapper and
overriding getCacheAwareContextLoaderDelegate(); however, this required
that the user configure the custom TestContextBootstrapper via
@BootstrapWith.
This commit introduces a new
"spring.test.context.default.CacheAwareContextLoaderDelegate" property
that can be configured via a JVM system property or via the
SpringProperties mechanism. BootstrapUtils uses this new property to
load the default CacheAwareContextLoaderDelegate. If the property is
not defined, BootstrapUtils will fall back to creating a
DefaultCacheAwareContextLoaderDelegate as it did previously.
This allows third parties to configure the default
CacheAwareContextLoaderDelegate transparently for the user -- for
example, to intercept context loading in order to load the context in a
different manner -- for example, to make use of ahead of time (AOT)
techniques for implementing a different type of ApplicationContext at
build time.
Closes gh-27540
This commit makes sure that the Reactor context from a given mono or
flux is propagated to the Flux returned by a FluxSink. This change
affects both DataBufferUtils::write and internal classes used by the
DefaultPartHttpMessageReader.
Closes gh-27517
Due to an SSL/TLS issue with hamcrest.org, the Dokka task fails with the
following.
> Failed to download package-list from https://hamcrest.org/JavaHamcrest/javadoc/2.1/package-list,
> this might suggest that remote resource is not available, module is
> empty or dokka output got corrupted
See: https://github.com/hamcrest/JavaHamcrest/issues/280
As a workaround, this commit switches to javadoc.io to reference the
Hamcrest Javadoc APIs.
No need to log the full exception for a resolved exception, and as the
comment suggests that it mirrors Spring MVC equivalent, which also
logs the message only.
PR gh-24470 introduced a regression for Android users by no longer
escaping closing curly braces in regular expressions.
This commit therefore partially reverts the changes made in 273812f9c5
for closing curly braces (`}`).
Closes gh27467
Previous to this commit, the specificity and quality comparators
(used by MediaType::sortByQualityValue and MediaType::sortBySpecificity)
could result in IllegalArgumentExceptions when used for sorting.
The underlying reason was that the comparators were not transitive, and
both media types with the same type, and types with the same amount of
parameters, would be considered identical by the comparator (result 0).
This commit ensures that the comparators are transitive.
Closes gh-27488
In order to catch Javadoc errors in the build, we now enable the
`Xwerror` flag for the `javadoc` tool. In addition, we now use
`Xdoclint:syntax` instead of `Xdoclint:none` in order to validate
syntax within our Javadoc.
This commit fixes all resulting Javadoc errors and warnings.
This commit also upgrades to Undertow 2.2.12.Final and fixes the
artifact names for exclusions for the Servlet and annotations APIs.
The incorrect exclusion of the Servlet API resulted in the Servlet API
being on the classpath twice for the javadoc task, which resulted in the
following warnings in previous builds.
javadoc: warning - Multiple sources of package comments found for package "javax.servlet"
javadoc: warning - Multiple sources of package comments found for package "javax.servlet.http"
javadoc: warning - Multiple sources of package comments found for package "javax.servlet.descriptor"
javadoc: warning - Multiple sources of package comments found for package "javax.servlet.annotation"
Closes gh-27480
Prior to this commit, all white space was trimmed from Server Sent Event
data. After this commit, only a leading space is removed (if present).
Closes gh-27473
In order to be able to use text blocks and other new Java language
features, we are upgrading to a recent version of Checkstyle.
The latest version of spring-javaformat-checkstyle (0.0.28) is built
against Checkstyle 8.32 which does not include support for language
features such as text blocks. Support for text blocks was added in
Checkstyle 8.36.
In addition, there is a binary compatibility issue between
spring-javaformat-checkstyle 0.0.28 and Checkstyle 8.42. Thus we cannot
use Checkstyle 8.42 or higher.
In this commit, we therefore upgrade to spring-javaformat-checkstyle
0.0.28 and downgrade to Checkstyle 8.41.
This change is being applied to `5.3.x` as well as `main` in order to
benefit from the enhanced checking provided in more recent versions of
Checkstyle.
Closes gh-27481
In 5.3 it became possible to handle exceptions from any handler through
ExceptionHandler's in a ControllerAdvice class, but this is not
mentioned in the docs
See gh-22619, gh-27338
Since the team no longer needs the ability to treat Eclipse projects as
WTP modules, this commit removes the obsolete custom WTP configuration
for importing projects into Eclipse IDE.
See gh-27407
In order to allow developers to execute TestNG tests in Eclipse IDE
without installing the TestNG plugin for Eclipse, this commit introduces
a JUnit Platform @Suite class that can be executed within the IDE.
See gh-27407
When not excluded, TestNG will pick up nested TestCase classes and run
them.
This commit therefore filters out `*TestCase` test classes from the
build since these are not intended to be executed with the build.
See gh-27406
Prior to this commit, we had configured separate test tasks for JUnit
and TestNG. In addition, we configured a standard `test` task that
depended on the `junit` and `testNG` tasks, and we had an additional
`aggregateTestReports` task that aggregated the reports from the JUnit
and TestNG test tasks.
Thanks to the introduction of the "TestNG Engine for the JUnit
Platform", this commit simplifies our Gradle build in the spring-test
module by running JUnit 4, JUnit Jupiter, and TestNG tests on the JUnit
Platform in a single Gradle `test` task.
See gh-27406
Prior to this commit, calling `StringUtils#collectionToDelimitedString`
would fail with an NPE if the collection contains null elements.
This commit ensures that null elements are converted as `"null"` in the
resulting String without failure.
See gh-27419
The migration to Gradle 7.2 resulted in a regression for our Eclipse
IDE support: several projects ended up with recursive classpath entries
in their generated .classpath files which prevent those projects from
being built within Eclipse.
This commit addresses this issue with a solution that may well be a
"hack". Nonetheless, a working hack is better than not being able to
import into Eclipse at all.
See gh-26870
This upgrade avoids warnings about the following on Gradle 7.1+.
- The Report.destination property has been deprecated.
- The JavaExec.main property has been deprecated.
See gh-26870
Migrate `CoroutinesUtils` from Kotlin code to Java and drop the
`kotlin-coroutines` module.
This update removes the need for Kotlin tooling IDE plugins to be
installed.
Closes gh-27379
HttpMessageConverterExtractor uses MessageBodyClientHttpResponseWrapper
which may read the first byte of the response stream to check if there
is content. After that it is necessary to use the wrapper to get the
full body.
This commit ensures that when UnknownContentTypeException is raised
it gets the body through the wrapper, or otherwise the first byte is
missed if the InputStream is not markable.
Closes gh-27374
To support the recent changes to our `optional` dependencies plugin,
this commit removes the Eclipse-specific code which no longer appears
to be necessary.
Closes gh-27365
This commit ensures that Servlet 4.0+ is used in the Spring OXM test
suite, as Servlet 4 specific APIs are used in the tests.
This problem was uncovered while fixing gh-27365
This allows the attributes configured on compileClasspath and
runtimeClasspath to independently influence the variant selection when
resolving the optional configuration, allowing it to contribute compile
dependencies (JAVA_API) to the former and runtime dependencies
(JAVA_RUNTIME) to the latter.
Fixes gh-27365
Previously, the optional configuration had no usage attribute. This
resulted in it using the default, JAVA_RUNTIME, which caused it to
only consume the runtime produced by its dependencies and not the
API. Given that the optional configuration is added to the compile
classpath, this was incorrect.
This commit updates the optional configuration to be configured to
consume the Java API of its dependencies. The configuration has
also been marked as not being for consumption. This prevents other
projects attempting to consume the optional variant of a project
that has the optional dependencies plugin applied and further
aligns it with Gradle's built-in configurations of a similar nature.
See gh-27365
This commit updates the defaultResponseCharacterEncoding() `default`
method in ConfigurableMockMvcBuilder so that it throws an
UnsupportedOperationException instead of silently ignoring the user's
request to set the default response character encoding.
Note, however, that AbstractMockMvcBuilder already overrides the
default method with a concrete implementation which is used by default
in MockMvc.
See gh-27230
This commit applies several optimizations to StringUtils#cleanPath and
related methods:
* pre-size pathElements deque in StringUtils#cleanPath with
pathElements.length elements, since this this is the maximum size and
the most likely case.
* optimize StringUtils#collectionToDelimitedString to calculate the size
of the resulting String and avoid array auto-resizing in the
StringBuilder.
* If the path did not contain any components that required cleaning,
return the (normalized) path as-is. No need to concatenate the prefix
and the trailing path.
See gh-26316
This commit also fixes a bug introduced in commit e99b43b91e, where
java.time.Duration strings were converted to milliseconds and then
converted again using the configured TimeUnit.
See gh-27309
This commit introduces a new `timeUnit` attribute in the @Scheduled
annotation to allow the user to specify a time unit other than
milliseconds.
Closes gh-27309
It happens very often that WebTestClient is used in heavyweight
integration tests, and it's a hindrance to developer productivity to
fix one failed assertion after another. Soft assertions help a lot by
checking all conditions at once even if one of them fails.
This commit introduces a new expectAllSoftly(..) method in
WebTestClient to address this issue.
client.get().uri("/hello")
.exchange()
.expectAllSoftly(
spec -> spec.expectStatus().isOk(),
spec -> spec.expectBody(String.class).isEqualTo("Hello, World")
);
Closes gh-26969
It happens very often that MockMvc is used in heavyweight integration
tests. It's no use to waste time to check if another condition has been
fixed or not. Soft assertions help a lot by checking all conditions at
once even if one of them fails.
See gh-26917
Co-authored-by: Sach Nguyen <sachnbbkhn@gmail.com>
Prior to this commit, if the user tested file upload support with
HtmlUnit and MockMvc by invoking HtmlFileInput.setData() instead of
HtmlFileInput.setFiles(), the in-memory file data was simply ignored.
This commit addresses this issue by creating a MockPart from the
in-memory data in HtmlUnitRequestBuilder.
Closes gh-27199
Prior to this commit, the hasContributors() method incorrectly returned
false if contributors had been configured.
This commit fixes the logic in hasContributors() and documents it.
Closes#27271
To improve the developer experience and avoid the use of String
literals, this commit provides overloaded support via Charset for
character encoding in MockHttpServletRequestBuilder and
ContentResultMatchers.
Closes gh-27231
Commit e4b9b1fadb introduced support for setting the default character
encoding in MockHttpServletResponse.
This commit introduces support for configuring the default character
encoding in the underlying MockHttpServletResponse used in MockMvc.
Closes gh-27230
Prior to this commit, MockMvc applied global ResultMatchers before
global ResultHandlers. This lead to unexpected scenarios where a
failing matcher would prevent a handler from being applied.
One concrete use case is `alwaysDo(print(System.err))` which should
print out MockMvc results for debugging purposes. However, if MockMvc is
configured with something like `alwaysExpect(content().string("?"))`
and the expectation fails, the user will never see the expected debug
output to help diagnose the problem.
This commit addresses this issue by applying global ResultHandlers
before ResultMatchers in MockMvc.
Closes gh-27225
Prior to this commit, it was possible to set the character encoding
in MockHttpServletResponse via setCharacterEncoding() or
setContentType(); however, those methods append "charset=..." to the
Content-Type header which may not be an acceptable side effect.
This commit addresses this shortcoming by introducing a new
setDefaultCharacterEncoding() in MockHttpServletResponse which allows
one to override the previously hard coded value of "ISO-8859-1". In
addition, setDefaultCharacterEncoding() does not modify the Content-Type
header.
The reset() method has also been updated to reset the character encoding
to the configured default character encoding.
Closes gh-27214
This commit improves the documentation for @Cacheable to point out that
`null` will be stored in the cache for an empty `Optional` return value.
Closes gh-27184
Prior to this commit, if the TaskExecutor configured in
WebSocketMessageBrokerStats for the inboundChannelExecutor or
outboundChannelExecutor was not a ThreadPoolTaskExecutor, a
StringIndexOutOfBoundsException was thrown when attempting to parse the
results of invoking toString() on the executor.
The reason is that ThreadPoolTaskExecutor delegates to a
ThreadPoolExecutor whose toString() implementation generates text
containing "pool size = ...", and WebSocketMessageBrokerStats'
getExecutorStatsInfo() method relied on the presence of "pool" in the
text returned from toString().
This commit fixes this bug by ensuring that the text returned from
toString() contains "pool" before parsing the text. If "pool" is not
present in the text, getExecutorStatsInfo() now returns "unknown"
instead of throwing a StringIndexOutOfBoundsException.
Closes gh-27209
A side effect of 71995a9087 caused the
dynamic table of contents in the left-hand side navigation to no longer
be displayed, likely due to the missing "details" DIV.
This commit addresses this issue by applying the custom header only to
index.adoc.
Consequently, the TOC is now displayed again on all pages except the
index page, but the customized header is no longer applied to those
pages.
We may revisit this issue if we decide that we want the custom header
on all pages (and not just the index page).
Closes gh-27177
If the ThreadPoolTaskExecutor is dynamically changed with an invalid value
the state of the ThreadPoolTaskExecutor does no longer correctly represent
the state of the underlying ThreadPoolExecutor
This commit makes JettyServerHttpRequest aware of
HttpServletRequestWrapper, and JettyServerHttpResponse aware of
HttpServletResponseWrapper.
Closes gh-27146
Before this commit, JettyClientHttpResponse checked for the presence of
a server-side class to determine whether it is running on Jetty 10.
Unfortunately, that class is not necessarily present when just using the
Jetty client.
This commit improves the Jetty 10 check, so that it also works when
the Jetty client is used without the server.
Closes gh-27136
This commit makes sure that we no longer use the internal API in the
Jetty support for the WebClient. With this change, we are able to
support both Jetty 9, 10, and 11.
Closes gh-27112
This reverts commit d6df4a6577 because running
gradle generatePomFileForMavenJavaPublication throws a
kotlin.KotlinNullPointerException error with Kotlin 1.5.20.
Revert Mockito upgrade done in 5d919dc094 because
Byte Buddy transitive upgrade from 1.11.1 to 1.11.3 seems to break Mockk tests
with java.security.AccessControlException related errors, so probably
better to wait Mockito using Byte buddy 1.11.5+ which seems to refine
this area, see https://github.com/raphw/byte-buddy/releases/tag/byte-buddy-1.11.5.
To slightly improve performance, this commit switches to
StringBuilder.append(char) instead of StringBuilder.append(String)
whenever we append a single character to a StringBuilder.
Closes gh-27098
Prior to this commit, ConfigurationClass implemented equals(),
hashCode(), and toString(), but BeanMethod did not.
This commit introduces equals(), hashCode(), and toString()
implementations in BeanMethod for consistency with ConfigurationClass
to make it possible to use BeanMethod instances to index additional
metadata as well.
In order to properly implement equals() in BeanMethod, the method
argument types are required, but these are not directly available in
BeanMethod. However, they are available via ASM when processing @Bean
methods. This commit therefore implements equals(), hashCode(), and
toString() in SimpleMethodMetadata which BeanMethod delegates to.
For completeness, this commit also implements equals(), hashCode(), and
toString() in StandardClassMetadata, StandardMethodMetadata, and
SimpleAnnotationMetadata.
Closes gh-27076
Prior to this commit, the toString() implementation did not separate
method argument types with a comma or any form of separator, leading
to results such as:
org.example.MyClass.myMethod(java.lang.Stringjava.lang.Integer)
instead of:
org.example.MyClass.myMethod(java.lang.String,java.lang.Integer)
Closes gh-27095
This commit defines the doc-root and api-spring-framework attributes
once in docs.gradle instead of duplicating them in each *.adoc file.
This commit also introduces a new docs-spring-framework global
attribute.
This commit disables the automatic header generation from Asciidoc's
default template and replaces it with a custom header that omits the
"Version" label before the revision number. The revision number is also
displayed in a simple span tag in order to reduce the amount of
vertical space taken by the header.
Prior to this commit, if a PathContainer was created using
Options.MESSAGE_ROUTE, DefaultPathSegment#parameters() returned a
mutable map which would allow the user to modify the contents of the
static, shared EMPTY_PARAMS map in DefaultPathContainer.
This commit prevents corruption of the shared EMPTY_PARAMS map by
ensuring that parameters stored in DefaultPathSegment are always
immutable.
Closes gh-27064
This commit revisits the recently updated `PORT_PATTERN` in
`UriComponentsBuilder`. The fix introduced in gh-26905 fails with
ambiguous URL patterns, especially when the port and path parts of the
pattern are hard to differentiate, for example
"https://localhost:{port}{path}".
This commit reinstates the previous behavior without undoing the actual
fix. The only limitation introduced here is the fact that only a single
pattern variable is allowed for the port pattern part.
Fixes gh-27039
Prior to this commit, the `HttpComponentsClientHttpConnector`
implementation could accept or create a default `HttpClient` instance
but not expose it as part of its API. This effectively prevents
applications from properly closing the associated resources when
disposing of the connector.
This commit implements the `Closeable` interface on the connector to
allow this use case.
Closes gh-27032
Proposed change aimed to keep coherence between variable declaration
and static initialization code, which stores 9 values, not 8, in these
two maps.
Closes gh-27016
Prior to this commit, in some cases application context startup steps
could be created concurrently, which could cause issues with the current
implementation tracking the parent/child relationship between steps.
This commit ensures that the flight recorder implementation is using
thread safe collection implementations for that.
Fixes gh-26941
Make sure that we use the parameter name in MultipartBodyBuilder::part
when adding a Part, instead of using the name specified in the
'Content-Disposition' header that might have been in the part's headers.
Closes gh-27007
This commit improves the Javadoc regarding transactional semantics for
@TransactionalEventListener methods invoked in the AFTER_COMMIT,
AFTER_ROLLBACK, or AFTER_COMPLETION phase. Specifically, the
documentation now points out that interactions with the underlying
transactional resource will not be committed in those phases.
Closes gh-26974
Prior to this commit, the `RouterFunctionMapping` WebFlux.fn variant
would set the `HandlerMapping.BEST_MATCHING_PATTERN_ATTRIBUTE` as an
exchange attribute. This is useful for instrumentation purposes.
The WebMvc.fn variant would not do the same; this would lead to
"UNKNOWN" path metrics tags.
This commit ensures that the `RouterFunctionMapping` WebMvc.fn variant
does set the `BEST_MATCHING_PATTERN_ATTRIBUTE` and
`BEST_MATCHING_HANDLER_ATTRIBUTE` request attributes.
Closes gh-26963
Many of the utility methods in ScriptUtils are public only because they
were once invoked from JdbdTestUtils in spring-test, which is no longer
the case. Consequently, there should no longer be a need for any
external clients to invoke such methods.
To address this, this commit formally deprecates the following methods
in ScriptUtils in spring-jdbc.
- readScript(...)
- containsSqlScriptDelimiters(...)
- splitSqlScript(...)
Closes gh-26947
Prior to this commit, many of the utility methods in ScriptUtils in
spring-r2dbc were public by accident: they were copied from ScriptUtils
in spring-jdbc without changing the visibility when spring-r2dbc was
introduced in Spring Framework. 5.3 GA.
This commit corrects this mistake by removing internal APIs from
ScriptUtils in spring-r2dbc from the public contract.
See gh-26947
This commit picks up where 569ce840cf left off, by correctly invoking
the new containsStatementSeparator(...) method from
executeSqlScript(...) in ScriptUtils in spring-r2dbc.
See gh-26911
Prior to this commit, the implementations of
ScriptUtils.containsSqlScriptDelimiters() in spring-jdbc and
spring-r2dbc did not ignore comments when searching for the statement
delimiter within an SQL script. This resulted in subtle bugs if a
comment contained a single single-quote or single double-quote, since
the absence of the closing single-quote or double-quote led the
algorithm to believe that it was still "within a text literal". Similar
issues could arise if a comment contained the sought statement
delimiter but the rest of the script did not contain the sought
statement delimiter. In such cases, the algorithms in ScriptUtils could
erroneously choose an incorrect statement delimiter -- for example,
using the fallback statement delimiter instead of the delimiter
specified by the user.
This commit avoids such bugs by ignoring single-line comments and block
comments when searching for the statement delimiter within an SQL
script.
Closes gh-26911
Prior to this commit, the containsSqlScriptDelimiters() method in
ScriptUtils ignored delimiters enclosed in single quotes but not those
enclosed within double quotes, which contradicts the algorithm in
splitSqlScript() and therefore constitutes a bug.
This commit fixes this bug in the ScriptUtils implementations in
spring-jdbc and spring-r2dbc.
Closes gh-26935
This commit makes sure that the DefaultPartHttpMessageReader uses a
random temporary directory to store uploaded files, so that two
instances do not collide.
See gh-26931
This commit makes sure that Synchronoss uses a random temporary
directory to store uploaded files, so that two instances do not collide.
Closes gh-26931
Recent commit dddcc5e9ad ensured a
trailing "/" in the Origin header has no effect. This commit does the
same for a trailing "/" in configured patterns.
See gh-26892
The pattern was changed in 65797d04f2
to check for characters up until "/", instead of for digits, but now
also checks up until "?" and "#".
Closes gh-26905
Prior to this commit, when Web MVC attempted to resolve a constructor
argument for a data class constructor with @ModelAttribute binding,
ModelAttributeMethodProcessor failed to unwrap the array returned by
WebRequest.getParameter(String).
According to the Javadoc for WebRequest.getParameter(String), "a
single-value parameter will be exposed as an array with a single
element."
This commit fixes this issue by extracting the single value from such
an array and using that as the constructor argument (potentially
converted by the WebDataBinder).
Closes gh-25200
This commit revises the fix submitted in 959e6d1745 by ensuring that
empty file input is converted to a MockPart with the supplied name, an
empty filename, "application/octet-stream" as the content type, and
empty content.
This aligns with the behavior of Servlet containers, as tested with the
interaction between Firefox and a standard Servlet running in a Jetty
Servlet container.
Closes gh-26799
Prior to this commit, when using HtmlUnit with empty file input,
MockMvc's HtmlUnitRequestBuilder would throw a NullPointerException
when attempting to create a MockPart based on the null File.
This commit ensures that empty file input is converted to a MockPart
with a valid name but with a null filename, a null content type, and
empty content.
Closes gh-26799
Prior to this commit, we registered custom values in the build scan for
the main and test toolchains based on input values provided via the
mainToolchain and testToolchain project properties.
Beginning with this commit, the custom values we register are based on
the available metadata for the resolved JDK/JVM for each toolchain.
For example, instead of registering the following custom value...
Test toolchain : JDK11
... we now register the following which includes the vendor, version,
and installation path of the JDK/JVM.
Test toolchain : AdoptOpenJDK 11 (/Library/Java/JavaVirtualMachines/adoptopenjdk-11.jdk/Contents/Home)
Once Gradle's JavaInstallationMetadata includes the exact version, we
will likely use that instead of the installation path.
See gh-25787
Prior to this commit, the task parameters for the CI project checks were
overridden by a task anchor. This commit splits the anchor declaration
and ensures that the `TEST_TOOLCHAIN` setting is set for the JDK
variant builds.
See gh-25787
Commit 3eec27a723 introduced a custom resource filter for projects
imported into Eclipse IDE. However, commit 85eb589c2e introduced
generated source files within the Gradle 'build' folder, and the filter
prevents Eclipse from seeing the generated sources, resulting in build
errors within the spring-oxm project in Eclipse.
This commit therefore effectively reverts 3eec27a723 by removing the
resource filter.
See gh-25787
Prior to this commit, @ModelAttribute(binding=false) was honored with
Spring Web MVC but not with WebFlux.
This commit adds support for disabling binding via @ModelAttribute with
WebFlux by adding a check to resolveArgument(...) in
ModelAttributeMethodArgumentResolver.
Closes gh-26856
This commit fixes various issues with the configuration of the Gradle
Java toolchain in the build.
First, the configuration of build properties is fixed in the CI pipeline
because it wasn't properly checked.
The JMH plugin is also upgraded and we now configure its toolchain
support.
This commit also rewrites the XJC tasks in the spring-oxm module,
leveraging a Gradle plugin that creates actual compile tasks we can
configure.
See gh-25787
This commit makes sure that LinkedCaseInsensitiveMap::computeIfAbsent
honors the contract of the method, and also replaces the old entry if
that mapped to null.
Closes gh-26868
This commit makes sure that LinkedCaseInsensitiveMap::putIfAbsent honors
the contract of the method, and also replaces the old entry if that
mapped to null.
Closes gh-26868
This commit fixes a potential memory leak, since PropertyComparator
previously kept an indirect reference to the value it last compared.
Closes gh-26869
This commit makes sure that any error handlers registered on the route
are also applied when an error occurs asynchronously. This commit
applies to asynchronous bodies with both CompletableFuture and Reactive
Streams, as well as completely asynchronous responses.
Closes gh-26831
Prior to this commit, MySQLMaxValueIncrementer could not be used when
the MySQL database was configured to use safe-updates mode.
See https://dev.mysql.com/doc/refman/8.0/en/mysql-tips.html#safe-updates
This commit introduces a `limit 1` clause to the generated update
statement to allow MySQLMaxValueIncrementer to be compatible with
MySQL safe-updates mode.
Closes gh-26858
Before this commit, HttpStatus::resolve used the values() method in its
logic. This causes a new array to be allocated for each invocation,
and results in memory overhead.
This commit makes a copy of the HttpStatus values array, and uses that
to resolve status codes.
Closes gh-26842
Prior to this commit, evaluating validation hints for
@javax.validation.Valid caused exceptions being raised when getting the
value of this annotation, which does not exist. Bypassing
AnnotationUtils.getValue() in those cases can improve performance by
avoiding the cost incurred by raising exceptions.
See gh-26787
Prior to this commit, two tests for exception handling regarding
@DateTimeFormat processing only passed on Java 8. This is due to the
fact that the toString() implementation for annotations changed in Java
9. Specifically, the representation for arrays changed from [] to {},
and strings are enclosed in double quotes beginning with Java 9.
This commit ensures that the affected @DateTimeFormat tests pass on
Java 9+, by making the assertions more lenient regarding toString()
output for annotations.
See gh-26777
See gh-26804
The support for fallback parsing patterns in @DateTimeFormat introduced
in gh-20292 introduced a regression in that the original cause of the
parsing exception was no longer retained.
gh-26777 addressed that regression for `java.time` support; whereas,
this commit addresses that regression for legacy Date types.
This commit ensures that the original ParseException is set as the
cause for any newly created ParseException, thereby retaining the
original exception as the root cause.
Closes gh-26804
The support for fallback parsing patterns in @DateTimeFormat introduced
in gh-20292 introduced a regression in that the original cause of the
parsing exception was no longer retained.
This commit ensures that the original DateTimeParseException is set as
the cause for any newly created DateTimeParseException, thereby
retaining the original exception as the root cause.
Closes gh-26777
Some operating systems delete temp files not just when booting up, but
also during operation. This commit makes sure that the
DefaultPartHttpMessageReader recreates the directory used to store
files in, if it's not there.
Closes gh-26790
This commit allows the spring-expression module to be more easily repackaged
for embedding in third-party JARs -- for example, via the Shadow Gradle plugin.
Closes gh-26779
This commit introduces support in both servlet and webflux for the
"Accept-Patch" header, which is sent when the client sends unsupported
data in PATCH requests.
See section 2.2 of RFC 5789.
Closes gh-26759
This commit introduces support in both servlet and webflux for the
"Accept-Patch" header in OPTIONS requests, as defined in section 3.1 of
RFC 5789.
See gh-26759
This commit adds support for Kotlin non-nullable type which resolves
to primitive Java types in BridgeMethodResolver#findBridgedMethod.
Closes gh-26585
Prior to this commit, if a test class annotated with @DirtiesContext
and @EnabledIf/@DisabledIf with `loadContext = true` was disabled due
to the evaluated SpEL expression, the ApplicationContext would not be
marked as dirty and closed.
The reason is that @EnabledIf/@DisabledIf are implemented via JUnit
Jupiter's ExecutionCondition extension API which results in the entire
test class (as well as any associated extension callbacks) being
skipped if the condition evaluates to `disabled`. This effectively
prevents any of Spring's TestExecutionListener APIs from being invoked.
Consequently, the DirtiesContextTestExecutionListener does not get a
chance to honor the class-level @DirtiesContext declaration.
This commit fixes this by implementing part of the logic of
DirtiesContextTestExecutionListener in
AbstractExpressionEvaluatingCondition (i.e., the base class for
@EnabledIf/@DisabledIf support). Specifically, if the test class for an
eagerly loaded ApplicationContext is disabled,
AbstractExpressionEvaluatingCondition will now mark the test
ApplicationContext as dirty if the test class is annotated with
@DirtiesContext.
Closes gh-26694
This commit fixes the missing pieces in our Maven Central publication
pipeline. Our first attempt at releasing with it showed a few problems:
* the promote task did not have the artifacts downladed with the
artifactory repository
* we applied the wrong Sonatype credentials to the task
* the github changelog task would fail because of docker rate limiting
since we were not using the right type of resource, which is
configured with the proper caching mechanism
See gh-26654
Prior to this commit, the Spring Framework build would rely on
setting a custom Java HOME for building all sources and tests
with that JDK.
This approach is not flexible enough, since we would be testing
the source compatibility against a recent JDK, but not a common
case experienced by the community: compiling and running
application code with a recent JDK and the official, JDK8-based
Framework artifacts.
This method is also limiting our choice of JDKs to the ones
currently supported by Gradle itself.
This commit introduces the support of Gradle JVM Toolchains in
the Spring Framework build.
We can now select a specific JDK for compiling the main
SourceSets (Java, Groovy and Kotlin) and another one for
compiling and running the test SourceSets:
`./gradlew check -PmainToolChain=8 -PtestToolchain=15`
Gradle will automatically find the JDKs present on the host or
download one automcatically. You can find out about the ones
installed on your host using:
`./gradlew -q javaToolchains`
Finally, this commit also refactors the CI infrastructure to:
* only have a single CI image (with all the supported JDKs)
* use this new feature to compile with JDK8 but test it
against JDK11 and JDK15.
Closes gh-25787
We now support Oracle's bind marker scheme that identifies dynamic
parameters using names that are prefixed with a colon such as
`:P0_myparam`.
Closes gh-26680
Prior to this commit, @DateTimeFormat only supported a single format
for parsing date time values via the style, iso, and pattern attributes.
This commit introduces a new fallbackPatterns attribute that can be
used to configure multiple fallback patterns for parsing date time
values. This allows applications to accept multiple input formats for
date time values.
For example, if you wish to use the ISO date format for parsing and
printing but allow for lenient parsing of user input for various
additional date formats, you could annotate a field or method parameter
with configuration similar to the following.
@DateTimeFormat(
iso = ISO.DATE,
fallbackPatterns = { "M/d/yy", "dd.MM.yyyy" }
)
Closes gh-20292
This commit skips the Bintray-related tasks in our CI pipeline and
instead relies on Maven Central for publishing Spring Framework
artifacts.
This commit also updates the CI pipeline to sign the artifacts directly
with the `artifactory-resource`.
Closes gh-26654
Previously we registered 3 AsyncListener's from the request, from the
response, and from the Servlet adapter.
After this change, only the Servlet adapter registers a listener and
the others are delegated to. This consolidates the handling of
AsyncListener events so that it's easier to discover, trace, and
enforce the order of handling.
See gh-26434
Prior to this commit, a method-level @CrossOrigin maxAge value did not
override a class-level @CrossOrigin maxAge value. This contradicts the
Javadoc for @CrossOrgin which states the following.
For those attributes where only a single value can be accepted such
as allowCredentials and maxAge, the local overrides the global
value.
This commit ensures that a method-level @CrossOrigin maxAge value
overrides a class-level @CrossOrigin maxAge value.
Closes gh-26619
Prior to this commit, `ServerHttpRequest.mutate()` would not reflect
changes made on the "Accept" and "Content-Type" HTTP headers.
This was due to the fact that the instantiation of a new request based
on the mutated values would not use the writable HTTP headers used
during the mutation, but rather a read-only view of the headers backed
by `ReadOnlyHttpHeaders`.
`ReadOnlyHttpHeaders` caches those values for performance reasons, so
getting those from the new request would not reflect the changes made
during the mutation phase.
This commit ensures that the new request uses the mutated headers.
Fixes gh-26615
This commit ensures handling is cancelled in case of onError/Timeout
callback from the Servlet container.
Separately we detect the same in ServletServerHttpRequest and
ServletServerHttpResponse, which signal onError to the read publisher
and cancel writing, but if the onError/Timeout arrives after reading
is done and before writing has started (e.g. longer handling), then
neither will reach handling.
See gh-26434, gh-26407
For setAsText, if the text argument is a file: URL for a path that does not exist, Paths.get(text) is called where text is a file: URL, which doesn't work - the result is an InvalidPathException.
To fix this issue, also check that the resource isn't a file before calling Paths.get(). That way, resources that are files skip to the other branch.
Class.getResource, ClassLoader.getResource, and ClassLoader.getSystemResource will throw IllegalArgumentException if a malformed URL is provided to them.
According to its javadoc, resolveURL should return null if not resolvable, so catch the IllegalArgumentException and return null.
Prior to this commit, the implementation of processKeyedProperty() in
AbstractNestablePropertyAccessor resulted in a
`java.lang.IllegalArgumentException: array element type mismatch` when
the property expression had more than one property key and the last key
should cause the array to grow automatically.
For example, given a property `int[][] multiArray` and property
expression `multiArray[1][3]`, the `processKeyedProperty()` method
created a new array object and assigned it to `multiArray`; whereas,
the new array object should have be assigned to `multiArray[1]`.
This commit fixes this issue.
Closes gh-26600
In order to reduce the focus on the deprecated @Required support, this
commit removes the RequiredAnnotationBeanPostProcessor section and
replaces it with a TIP and an updated NOTE.
See gh-26578
Since Spring Framework 5.2, the LoadTimeWeaver no longer weaves bean
classes annotated with @Component. This is a regression caused by the
changes in 40c62139ae, stemming from the fact that any class annotated
or meta-annotated with @Component is considered to be a candidate
configuration class in 'configuration lite' mode (i.e., a class without
the @Configuration annotation and without any @Bean methods) and
therefore now has its class eagerly loaded. This results in the class
being loaded before the LoadTimeWeaver has a chance to weave it.
This commit fixes this regression by explicitly avoiding eager class
loading for any 'lite' @Configuration or @Component class without @Bean
methods.
Closes gh-26199
Prior to this commit, `ResourceUrlProvider` would listen and consider
all `ContextRefreshedEvent` and use the given context to detect
`SimpleUrlHandlerMapping`.
This could lead to situations where a `ResourceUrlProvider` uses another
application context than its own (in a parent/child context setup) and
detect the wrong set of handlers.
Because `ResourceUrlProvider` locks itself once the auto-detection is
done, we need to ensure that it considers only events sent by its
application context.
Fixes gh-26561
Prior to this commit, MockHttpServletResponse only included the Expires
attribute in the generated Cookie header if the Max-Age attribute had
also been set.
This commit supports including the Expires attribute in the generated
Cookie Header even when the Max-Age attribute has not been set.
Closes gh-26558
Add factory methods to `AbstractEnvironment` that allow a custom
`ConfigurablePropertyResolver` and `MutablePropertySources` instance
to be used.
See gh-26462
With the introduction of the -H:+InlineBeforeAnalysis native image
compiler flag in GraalVM 21.0.0, it is now possible to use an utility method and get code
removal at build time.
This flag will be enabled as of Spring Native 0.9.0.
closes gh-25795
This commit updates the reference manual to point out that one may use
`.` instead of `$` as the nested class separator when providing a fully
qualified class name for a nested class in XML configuration.
This commit also updates the test for ClassUtils#forName to assert
support for `.` instead of `$`.
Closes gh-26540
gh-24281 introduced support to honor generic type information in
BeanUtils.copyProperties(), but that introduced a regression.
Specifically, if the supplied source or target object lacked generic
type information for the return type of the read-method or the
parameter type of the write-method for a given property, respectively,
the two properties would be considered a mismatch and ignored. This can
occur if the source or target object is a java.lang.reflect.Proxy since
the dynamically generated class for the proxy loses the generic type
information from interfaces that the proxy implements.
This commit fixes this regression by ignoring generic type information
if either the source or target property is lacking generic type
information.
Closes gh-26531
This commit better aligns how URI variable placeholders are detected
in UriComponentsBuilder#encode (i.e. the pre-encoding of the literal
parts of a URI template) and how they are expanded later on.
The latter relies on a pattern that stops at the first closing '}'
which excludes the possibility for well-formed, nested placeholders
other than variables with regex syntax, e.g. "{year:\d{1,4}}".
UriComponentsBuilder#encode now also stops at the first closing '}' and
further ensures the placeholder is not empty and that it has '{' before
deciding to treat it as a URI variable.
Closes gh-26466
This commit changes the condition in the if-block to check the number of
available processors instead of currently active threads with the hope
that doing so will prove more reliable on the CI server.
`spring-beans` ships a `YamlProcessor` that's used as a base class by
`YamlMapFactoryBean` and `YamlPropertiesFactoryBean`. These
implementations have a clear use case: mapping application-internal Yaml
documents for configuration or infrastructure purposes.
Since this use case rarely requires extended types support from the
underlying library, and since we're offering ways to list custom types
(since #25152), we'll restrict to java standard types only by default.
This simplifies the setup and focuses the abstract class on the core
use cases.
Closes gh-26530
This commit makes sure the StringDecoder supports stripping off
multi-line delimiters, such as \r\n. Specifically, we ensure that the
delimiter is stripped from the joined buffer.
Closes gh-26511
When a broker message handler is not configured with any prefixes, it will
process all messages by default, but user destination messages should be
pre-processed by the userDestinationMessageHandler first. This change
protects against that.
Closes gh-26474
This commit aligns the documentation in the reference manual with the
actual source code for StoredProcedure with regard to public execute()
methods.
Closes gh-26505
Previously this method returned headers only when a Content-Type part header
was present. Now it is guaranteed to return headers (possibly empty) as long
as there is a MultipartFile or Part with the given name.
Closes gh-26501
Prior to this commit, if an SQLException was thrown while retrieving
column metadata from the database, SimpleJdbcInsert would generate an
INSERT statement that was syntactically valid but missing columns,
which could lead to data silently missing in the database (for nullable
columns).
This commit fixes this by clearing all collected column metadata if an
SQLException is thrown while processing the metadata. The result is
that an InvalidDataAccessApiUsageException will be thrown later while
generating the INSERT statement. The exception message now contains an
additional hint to make use of SimpleJdbcInsert#usingColumns() in order
to ensure that all required columns are included in the generated
INSERT statement.
SimpleJdbcCall can also encounter an SQLException while retrieving
column metadata for a stored procedure/function, but an exception is
not thrown since a later invocation of the stored procedure/function
will likely fail anyway due to missing arguments. Consequently, this
commit only improves the warning level log message by including a hint
to make use of SimpleJdbcCall#addDeclaredParameter().
Closes gh-26486
Prior to this commit, calls to setLocale() MockHttpServletResponse
would result in a NullPointerException if the supplied Locale was null.
Although the Javadoc for setLocale(Locale) and addHeader(String, String)
in javax.servlet.ServletResponse does not specify how a null
Locale should be handled, both Tomcat and Jetty simply ignore a null
value.
This commit therefore updates MockHttpServletResponse to silently
ignore a null Locale passed to setLocale().
Closes gh-26493
Prior to this commit, calls to setHeader() and addHeader() in
MockHttpServletResponse would result in an IllegalArgumentException or
NullPointerException if the supplied header value was null.
Although the Javadoc for setHeader(String, String) and
addHeader(String, String) in javax.servlet.http.HttpServletResponse
does not specify how a null header value should be handled, both Tomcat
and Jetty simply ignore a null value. Furthermore,
org.springframework.http.HttpHeaders.add(String, String) declares the
headerValue parameter as @Nullable.
This commit therefore updates MockHttpServletResponse to silently
ignore null header values passed to setHeader() and addHeader().
Closes gh-26488
1. Update the HandlerMapping contract to state that CORS checks are expected
to be applied before returning a handler.
2. DispatcherHandler checks explicitly for pre-flight requests or CORS failed
requests and skips handling for both. Technically no change since
AbstractHandlerMapping already returns a NO_OP_HANDLER for those cases.
The purpose however is for the DispatcherHandler to also guarantee more
explicitly that no such handling can take place for such cases.
As one consequence, this makes it possible to invoke the DispatcherHandler from
anywhere in the WebFilter chain in order to "handle" a pre-flight request, and
then skip the rest of the WebFilter chain.
See gh-26257
Prior to this commit, if the DataSource in the
DataSourceFromTransactionManager was wrapped in a proxy implementing
InfrastructureProxy, SqlScriptsTestExecutionListener would throw an
exception stating that the DataSource in the ApplicationContext and the
DataSource in the DataSourceFromTransactionManager were not the same.
This commit unwraps both data sources and compares the underlying
target instances to check for equality.
In addition, this commit makes the unwrapResourceIfNecessary() method in
TransactionSynchronizationUtils public.
Closes gh-26422
This commit introduces warnings in invokeBeanFactoryPostProcessors()
and registerBeanPostProcessors() to deter people from submitting PRs
that result in breaking changes.
Closes gh-26401
Prior to this commit, `SimpleUrlHandlerMapping` and other
implementations of `AbstractUrlHandlerMapping` would not strip the
Servlet context path from the request path before performing path
matching with PathPattern instances.
This resulted in requests not matching as expected if the application
was configured with a Servlet context path.
This commit ensures that the `RequestPath` "path whithin the
application" is used for matching against path patterns.
Fixes gh-26411
This commit makes sure that the CronExpression rolls back the time to
midnight when dealing with Quartz expression fields (such as "L", "LW",
etc.).
Closes gh-26390
Remove support for open polymorphic serialization in
kotlinx.serialization web converters and codecs in order
to prevent serialization handling suitable for Jackson
or other general purpose Java JSON libraries.
This will probably need further refinements for collections
for example, and could ultimately be fixed when
kotlinx.serialization will provide a dedicated function to
evaluate upfront if a type can be serialized or not.
Closes gh-26298
This commit documents ApplicationContext initialization and shutdown
logging semantics for console output triggered in conjunction with the
Spring TestContext Framework.
Closes gh-25385
Prior to this commit, WebFlux native headers adapters would delegate the
`httpHeaders.keySet` to underlying implementations that do not honor the
`remove*` methods.
This commit fixes the `Set` implementation backing the
`httpHeaders.keySet` and ensures that headers can be safely removed from
the set.
Fixes gh-26361
Instead of using a new bounded elastic scheduler per
DefaultPartHttpMessageReader instance, which creates daemon threads that
are not shut down, we now use the shared bounded elastic scheduler.
Closes gh-26347
This commit only writes the 'charset' parameter in the written headers
if it is non-default (not UTF-8), since RFC7578 states that the only
allowed parameter is 'boundary'.
See gh-25885
Closes gh-26290
An empty buffer for RSocket is an empty message and while some codecs
such as StringDecoder may be able turn that into something such as an
empty String, for other formats such as JSON it is invalid input.
Closes gh-26344
Prior to this commit, the `ServletServerHttpResponse` would copy headers
from the `HttpHeaders` map and calls methods related to headers exposed
as properties (content-type, character encoding).
Unlike its reactive variant, this would not set the content length.
Depending on the Servlet container implementation, this could cause
duplicate Content-Length response headers in the actual HTTP response.
This commit aligns both implementations and ensures that the
`setContentLengthLong` method is called if necessary so that the Servlet
container can ensure a single header for that.
Fixes gh-26330
Prior to this commit, the `ResourceHttpRequestHandler` would write the
resource size to the "Content-Length" response header.
This is already done by the underlying `ResourceHttpMessageConverter`
and `ResourceRegionHttpMessageConverter`.
This commit avoid this duplicate operation and delegates instead to the
converters.
See gh-26330
Closes gh-26340
- Remove unused clone() code left-over from previous way of cloning.
- Lazy instantiation of ServerCodecConfigurer in
HttpWebHandlerAdapter since in most cases the configurer instance
is set externally.
Closes gh-26263
This commit reverts some changes done in 2d5f9723fa
in order to fix JdbcOperations.queryForObject and
JdbcOperations.queryForList.
It is not possible to provide a vararg variant in Kotlin
for now due to a signature clash, but that will probably
make sense in Spring Framework 6 timeframe along to array
based variant removal for both Java and Kotlin.
Closes gh-26312
Since support for the commandName attribute was removed from the
implementation of FormTag in Spring Framework 5.0, the presence of the
commandName attribute in the spring-form.tld file is no longer valid
and can lead one to assume that the commandName attribute is still
supported -- for example when using code completion in a JSP editor.
This commit therefore removes the obsolete commandName attribute in
spring-form.tld.
Closes gh-26337
This commit introduces tests that verify support for using
@PropertySource as a repeatable annotation without the
@PropertySources container, both locally on an @Configuration class
and on a custom composed annotation.
See gh-26329
This commit introduces a new feature in the Spring TestContext
Framework (TCF) that provides support for recording application events
published in the ApplicationContext so that assertions can be performed
against those events within tests. All events published during the
execution of a single test are made available via the ApplicationEvents
API which allows one to process the events as a java.util.Stream.
The following example demonstrates usage of this new feature.
@SpringJUnitConfig(/* ... */)
@RecordApplicationEvents
class OrderServiceTests {
@Autowired
OrderService orderService;
@Autowired
ApplicationEvents events;
@Test
void submitOrder() {
// Invoke method in OrderService that publishes an event
orderService.submitOrder(new Order(/* ... */));
// Verify that an OrderSubmitted event was published
int numEvents = events.stream(OrderSubmitted.class).count();
assertThat(numEvents).isEqualTo(1);
}
}
To enable the feature, a test class must be annotated or meta-annotated
with @RecordApplicationEvents. Behind the scenes, a new
ApplicationEventsTestExecutionListener manages the registration of
ApplicationEvents for the current thread at various points within the
test execution lifecycle and makes the current instance of
ApplicationEvents available to tests via an @Autowired field in the
test class. The latter is made possible by a custom ObjectFactory that
is registered as a "resolvable dependency". Thanks to the magic of
ObjectFactoryDelegatingInvocationHandler in the spring-beans module,
the ApplicationEvents instance injected into test classes is
effectively a scoped-proxy that always accesses the ApplicationEvents
managed for the current test.
The current ApplicationEvents instance is stored in a ThreadLocal
variable which is made available in the ApplicationEventsHolder.
Although this class is public, it is only intended for use within the
TCF or in the implementation of third-party extensions.
ApplicationEventsApplicationListener is responsible for listening to
all application events and recording them in the current
ApplicationEvents instance. A single
ApplicationEventsApplicationListener is registered with the test's
ApplicationContext by the ApplicationEventsTestExecutionListener.
The SpringExtension has also been updated to support parameters of type
ApplicationEvents via the JUnit Jupiter ParameterResolver extension
API. This allows JUnit Jupiter based tests to receive access to the
current ApplicationEvents via test and lifecycle method parameters as
an alternative to @Autowired fields in the test class.
Closes gh-25616
This new option allows a cancel signal to abort the request, which is
how we expect a connection to be aborted in a reactive chain that
involves the WebClient.
Closes gh-26287
This commit introduces computeAttribute() as an interface default method
in the AttributeAccessor API. This serves as a convenience analogous to
the computeIfAbsent() method in java.util.Map.
Closes gh-26281
Prior to this commit, the `NettyHeadersAdapter` would directly delegate
the `add()` and `set()` calls to the adapted
`io.netty.handler.codec.http.HttpHeaders`. This implementation rejects
`null` values with exceptions.
This commit aligns the behavior here with other implementations, by not
rejecting null values but simply ignoring them.
Fixes gh-26274
This commit makes sure that the matching pattern attributes is cleared
when an async result has been obtained, so that the subsequent
dispatch starts from scratch.
Closes gh-26239
This commit refines ConfigurationClassPostProcessor behavior in
native images by skipping configuration classes enhancement
instead of raising an error.
See spring-projects-experimental/spring-graalvm-native#248 for
more details.
Closes gh-26236
HttpMessageWriter implementations now attach the request log prefix
as a hint to created data buffers when the logger associated with
the writer is at DEBUG level.
Closes gh-26230
This commit updates websocket and messaging configurations in order
to not use CGLIB proxies anymore. The goal here is to allow support
in native executables and to increase the consistency across the
portfolio.
Closes gh-26227
The previous implementation uses ArrayList for storing resolved
resources and ArrayList has O(n) time complexity for the contains
operation. By switching to the HashSet for storing resolved
resources we improve the time complexity of this operation to be O(1).
See gh-25927
This commit improves the Javadoc for the `ForwardedHeaderFilter`
(Servlet Filter) and `ForwardedHeaderTransformer` (reactive variant) so
as to mention security considerations linked to Forwarded HTTP headers.
Closes gh-26081
Prior to this commit, the `SimpleApplicationEventMulticaster` would be
instrumented with the `ApplicationStartup` and start/stop events for
invoking event listeners (`spring.event.invoke-listener`).
This feature was already limited to single-threaded event publishers,
but is still flawed since several types of events can happen
concurrently. Due to the single-threaded nature of the startup sequence,
our implementation should not produce startup events concurrently.
This can cause issues like gh-26057, where concurrent events lead to
inconcistencies when tracking parent/child relationships.
This commit removes the `spring.event.invoke-listener` startup event as
a result.
Fixes gh-26057
This commit introduces AsyncServerResponse, an extension of
ServerResponse that is returned from ServerResponse.async and that
allows users to get the future response by calling the block method.
This is particularly useful for testing purposes.
This commit adds support for sending Server-Sent Events in WebMvc.fn,
through the ServerResponse.sse method that takes a SseBuilder DSL.
It also includes reference documentation.
Closes gh-25920
Remove the overriden pathVariable method from the nested request
wrapper,so that the merged attributes are used instead of the ones
provided by servlet.
Closes gh-26163
1. Revert changes in setHeader from 5.2.9 that caused regression on self-copy.
2. Update copyHeaders to ensure it still gets a copy of native headers.
3. Exit if source and target are the same instance, as an optimization.
Closes gh-26155
This commit introduces the following changes:
- Converters/codecs are now used based on generic type info.
- On WebMvc and WebFlux, kotlinx.serialization is enabled along
to Jackson because it only serializes Kotlin @Serializable classes
which is not enough for error or actuator endpoints in Boot as
described on spring-projects/spring-boot#24238.
TODO: leverage Kotlin/kotlinx.serialization#1164 when fixed.
Closes gh-26147
This commit only writes the 'charset' parameter in the written headers
if it is non-default (not UTF-8), since RFC7578 states that the only
allowed parameter is 'boundary'.
Closes gh-25885
Recently the Spring Framework projects could no longer be imported into
Eclipse IDE without compilation errors in JMH sources.
This commit addresses this issue by applying workarounds for bugs in
Gradle and the JMH plugin for Gradle.
Gradle bug: https://github.com/gradle/gradle/issues/14932
JMH plugin bug: https://github.com/melix/jmh-gradle-plugin/issues/157
The Gradle bug has already been fixed in Gradle 6.8 RC1; however, the
issue for the JMH plugin bug seems not to have been triaged yet.
Closes gh-26140
Despite the code duplication, we will not delegate to
AopUtils.invokeJoinpointUsingReflection() from
AbstractAspectJAdvice.invokeAdviceMethodWithGivenArgs().
The rationale is that the exception message in
invokeAdviceMethodWithGivenArgs() provides additional context via the
pointcut expression, and we would lose that additional context if we
simply delegate to AopUtils.invokeJoinpointUsingReflection(). We could
introduce an overloaded variant of invokeJoinpointUsingReflection() that
accepts an additional argument to provide the additional context for the
exception message, but we don't think that would be the best solution
for this particular use case.
In light of that, we are simply removing the TODO.
Closes gh-26126
Prior to this change the checks for isVariableName were duplicated
in 2 different locations. The logic has been moved to AspectJProxyUtils
to allow for re-use in those places and so that it benefits from any
optimizations that are done.
There are more locations which could benefit from not using a
toCharArray on a String, but rather use the charAt method from
the String itself. This to prevent an additional copy of the
char[] being created.
Prior to this commit, the promote task in the CI release pipeline would
write the "concourse-release-scripts" CONSOLE logs to /dev/null; this
commit ensures that we can read those while promoting artifacts.
gh-19930 introduced support for finding class-level test configuration
annotations on enclosing classes when using JUnit Jupiter @Nested test
classes, but support for @DynamicPropertySource methods got overlooked
since they are method-level annotations.
This commit addresses this shortcoming by introducing full support for
@NestedTestConfiguration semantics for @DynamicPropertySource methods
on enclosing classes.
Closes gh-26091
Prior to this commit, the test("test") conditions used in
AutowiredConfigurationErrorsIntegrationTests inadvertently asserted
that the invoked test methods reside in an org.springframework.test
subpackage, which is always the case for any test method in the
`spring-test` module. In other words, "test" is always a substring of
"org.springframework.test...", which is not a meaningful assertion.
This commit ensures that the JUnit Platform Test Kit is asserting the
actual names of test methods.
This commit introduces `and()` default methods in the MethodFilter and
FieldFilter functional interfaces in ReflectionUtils in order to simplify
uses cases that need to compose filter logic.
Closes gh-26063
Prior to this commit, a developer may have accidentally annotated a
JUnit Jupiter test method or lifecycle method with @Autowired, and that
would have potentially resulted in an exception that was hard to
understand. This is because the Spring container considers any
@Autowired method to be a "configuration method" when autowiring the
test class instance. Consequently, such an @Autowired method would be
invoked twice: once by Spring while attempting to autowire the test
instance and another time by JUnit Jupiter when invoking the test or
lifecycle method. The autowiring invocation of the method often leads
to an exception, either because Spring cannot satisfy a dependency (such
as JUnit Jupiter's TestInfo) or because the body of the method fails due
to test setup that has not yet been invoked.
This commit introduces validation for @Autowired test and lifecycle
methods in the SpringExtension that will throw an IllegalStateException
if any @Autowired method in a test class is also annotated with any of
the following JUnit Jupiter annotations.
- @Test
- @TestFactory
- @TestTemplate
- @RepeatedTest
- @ParameterizedTest
- @BeforeAll
- @AfterAll
- @BeforeEach
- @AfterEach
Closes gh-25966
The alternative is to use a filter but this makes it a little easier
and also guarantees that it will be downstream from all filters
regardless of their order, and therefore the Context will be visible
to all of them.
Closes gh-25710
In 5.3.x and forward, completely avoid logging unsent CONNECT messages
that are most likely authentication issues before the session is even
established.
Closes gh-26026
Adds a static INSTANCE to FullyQualifiedAnnotationBeanNameGenerator,
just like its parent class, AnnotationBeanNameGenerator, does.
The class doesn't have any state and overriding/hiding the INSTANCE of
the superclass, this prevents unintended use of a regular
AnnotationBeanNameGenerator through
FullyQualifiedAnnotationBeanNameGenerator.INSTANCE.
Prior to this commit, MergedAnnotationCollectors.toAnnotationSet()
created an intermediate ArrayList for storing the results prior to
creating a LinkedHashSet in the finishing step.
Since the creation of the intermediate list is unnecessary, this commit
simplifies the implementation of toAnnotationSet() by using the
Collector.of() factory method that does not accept a `finisher` argument.
The resulting Collector internally uses a `castingIdentity()` function
as the `finisher`.
Closes gh-26031
Prior to this commit, the findAllLocalMergedAnnotations() method in
AnnotationDescriptor altered between the use of TYPE_HIERARCHY and
TYPE_HIERARCHY_AND_ENCLOSING_CLASSES for the SearchStrategy, depending
on @NestedTestConfiguration semantics; however, when searching for
"local" annotations, there is no need to search the enclosing class
hierarchy since AnnotationDescriptor#next() handles that use case.
This commit therefore switches to using only the TYPE_HIERARCHY
strategy.
This commit also discontinues the use of
MergedAnnotationCollectors.toAnnotationSet() in order to avoid the
unnecessary creation of a temporary List when collecting synthesized
annotations in a LinkedHashSet.
Closes gh-25985
This commit configures the logging level to DEBUG for the concourse
release scripts tasks.
This is useful to get a clue on where those long-running tasks are at.
With this commit, bean definition profiles declared via @ActiveProfiles
are once again stored in registration order, in order to support use
cases in Spring Boot and other frameworks that depend on the
registration order.
This effectively reverts the changes made in conjunction with gh-25973.
Closes gh-26004
This commit makes copies of the default headers and cookies when a
WebClient is built, so that subsequent changes to these do not affect
previously built clients.
Closes: gh-25992
# <img src="src/docs/spring-framework.png" width="80" height="80"> Spring Framework [](https://ci.spring.io/teams/spring-framework/pipelines/spring-framework-5.3.x?groups=Build")
# <img src="src/docs/spring-framework.png" width="80" height="80"> Spring Framework [](https://ci.spring.io/teams/spring-framework/pipelines/spring-framework-5.3.x?groups=Build") [](https://ge.spring.io/scans?search.rootProjectNames=spring)
This is the home of the Spring Framework: the foundation for all [Spring projects](https://spring.io/projects). Collectively the Spring Framework and the family of Spring projects are often referred to simply as "Spring".
@@ -14,16 +14,20 @@ For access to artifacts or a distribution zip, see the [Spring Framework Artifac
## Documentation
The Spring Framework maintains reference documentation ([published](https://docs.spring.io/spring-framework/docs/current/spring-framework-reference/) and [source](src/docs/asciidoc)), Github [wiki pages](https://github.com/spring-projects/spring-framework/wiki), and an
The Spring Framework maintains reference documentation ([published](https://docs.spring.io/spring-framework/docs/current/spring-framework-reference/) and [source](src/docs/asciidoc)), GitHub [wiki pages](https://github.com/spring-projects/spring-framework/wiki), and an
[API reference](https://docs.spring.io/spring-framework/docs/current/javadoc-api/). There are also [guides and tutorials](https://spring.io/guides) across Spring projects.
## Micro-Benchmarks
See the [Micro-Benchmarks](https://github.com/spring-projects/spring-framework/wiki/Micro-Benchmarks) Wiki page.
See the [Micro-Benchmarks](https://github.com/spring-projects/spring-framework/wiki/Micro-Benchmarks) wiki page.
## Build from Source
See the [Build from Source](https://github.com/spring-projects/spring-framework/wiki/Build-from-Source) Wiki page and the [CONTRIBUTING.md](CONTRIBUTING.md) file.
See the [Build from Source](https://github.com/spring-projects/spring-framework/wiki/Build-from-Source) wiki page and the [CONTRIBUTING.md](CONTRIBUTING.md) file.
## Continuous Integration Builds
Information regarding CI builds can be found in the [Spring Framework Concourse pipeline](ci/README.adoc) documentation.
The Spring Framework is using https://concourse-ci.org/[Concourse] for its CI build and other automated tasks.
The Spring team has a dedicated Concourse instance available at https://ci.spring.io.
The Spring Framework uses https://concourse-ci.org/[Concourse] for its CI build and other automated tasks.
The Spring team has a dedicated Concourse instance available at https://ci.spring.io with a build pipeline
for https://ci.spring.io/teams/spring-framework/pipelines/spring-framework-5.3.x[Spring Framework 5.3.x].
=== Setting up your development environment
@@ -25,13 +26,17 @@ spring https://ci.spring.io spring-framework Wed, 25 Mar 20
----
=== Pipeline configuration and structure
The build pipelines are described in `pipeline.yml` file.
This file is listing Concourse resources, i.e. build inputs and outputs such as container images, artifact repositories, source repositories, notification services, etc.
It also describes jobs (a job is a sequence of inputs, tasks and outputs); jobs are organized by groups.
The `pipeline.yml` definition contains `((parameters))` which are loaded from the `parameters.yml` file or from our https://docs.cloudfoundry.org/credhub/[credhub instance].
You'll find in this folder the following resources:
* `pipeline.yml` the build pipeline
* `parameters.yml` the build parameters used for the pipeline
* `images/` holds the container images definitions used in this pipeline
@@ -41,6 +46,7 @@ You'll find in this folder the following resources:
=== Updating the build pipeline
Updating files on the repository is not enough to update the build pipeline, as changes need to be applied.
The pipeline can be deployed using the following command:
[source]
@@ -48,4 +54,4 @@ The pipeline can be deployed using the following command:
@@ -16,28 +16,32 @@ that STS 4 comes with Buildship preinstalled.
_When instructed to execute `./gradlew` from the command line, be sure to execute it within your locally cloned `spring-framework` working directory._
1.Ensure that Eclipse launches with JDK 8.
- For example, on Mac OS this can be configured in the `Info.plist` file located in the `Contents` folder of the installed Eclipse or STS application (e.g., the `Eclipse.app` file).
1. Install the [Kotlin Plugin for Eclipse](https://marketplace.eclipse.org/content/kotlin-plugin-eclipse) in Eclipse.
1.Install the [Eclipse Groovy Development Tools](https://github.com/groovy/groovy-eclipse/wiki) in Eclipse.
1. Switch to Groovy 2.5 (Preferences -> Groovy -> Compiler -> Switch to 2.5...) in Eclipse.
1.Change the _Forbidden reference (access rule)_ in Eclipse from Error to Warning
(Preferences -> Java -> Compiler -> Errors/Warnings -> Deprecated and restricted API -> Forbidden reference (access rule)).
1. Optionally install the [AspectJ Development Tools](https://marketplace.eclipse.org/content/aspectj-development-tools) (_AJDT_) if you need to work with the `spring-aspects` project. The AspectJ Development Tools available in the Eclipse Marketplace have been tested with these instructions using STS 4.5 (Eclipse 4.14).
1. Optionally install the [TestNG plugin](https://testng.org/doc/eclipse.html) in Eclipse if you need to execute TestNG tests in the `spring-test` module.
1.Install the [Groovy Development Tools](https://marketplace.eclipse.org/content/groovy-development-tools).
1. Switch to Groovy 3.0 in Eclipse (Preferences → Groovy → Compiler → Switch to 3.0...).
- If you encounter build errors stating something similar to _"Groovy: compiler mismatch: project level is 2.5, workspace level is 3.0"_, change the Groovy compiler version to 3.0 for each affected project.
1.Ensure that the _Forbidden reference (access rule)_ in Eclipse is set to `Info`
(Preferences → Java → Compiler → Errors/Warnings → Deprecated and restricted API → Forbidden reference (access rule)).
1.Optionally install the [Kotlin Plugin for Eclipse](https://marketplace.eclipse.org/content/kotlin-plugin-eclipse) if you need to execute Kotlin-based tests or develop Kotlin extensions.
- **NOTE**: As of September 21, 2021, it appears that the Kotlin Plugin for Eclipse does not yet work with Eclipse 4.21.
1. Optionally install the [AspectJ Development Tools](https://marketplace.eclipse.org/content/aspectj-development-tools) (_AJDT_) if you need to work with the `spring-aspects` project.
- **NOTE**: As of September 21, 2021, it appears that the AspectJ Development Tools do not yet work with Eclipse 4.21.
1. Optionally install the [TestNG plugin](https://testng.org/doc/eclipse.html) in Eclipse if you need to execute individual TestNG test classes or tests in the `spring-test` module.
- As an alternative to installing the TestNG plugin, you can execute the `org.springframework.test.context.testng.TestNGTestSuite` class as a "JUnit 5" test class in Eclipse.
1. Build `spring-oxm` from the command line with `./gradlew :spring-oxm:check`.
1. To apply project specific settings, run `./gradlew eclipseBuildship` from the command line.
1. Import into Eclipse (File -> Import -> Gradle -> Existing Gradle Project -> Navigate to the locally cloned `spring-framework` directory -> Select Finish).
1. To apply Spring Framework specific settings, run `./gradlew cleanEclipse eclipse` from the command line.
1. Import all projects into Eclipse (File → Import → Gradle → Existing Gradle Project → Navigate to the locally cloned `spring-framework` directory → Select Finish).
- If you have not installed AJDT, exclude the `spring-aspects` project from the import, if prompted, or close it after the import.
- If you run into errors during the import, you may need to set the _Java home_ for Gradle Buildship to the location of your JDK 8 installation in Eclipse (Preferences -> Gradle -> Java home).
1. If you need to execute JAXB-related tests in the `spring-oxm` project and wish to have the generated sources available, add the `build/generated-sources/jaxb` folder to the build path (right click on the `jaxb` folder and select `Build Path -> Use as Source Folder`).
- If you do not see the `build` folder in the `spring-oxm` project, ensure that the "Gradle build folder" is not filtered out from the view. This setting is available under "Filters" in the configuration of the Package Explorer (available by clicking on the small downward facing arrow in the upper right corner of the Package Explorer).
- If you run into errors during the import, you may need to set the _Java home_ for Gradle Buildship to the location of your JDK 8 installation in Eclipse (Preferences → Gradle → Java home).
1. If you need to execute JAXB-related tests in the `spring-oxm` project and wish to have the generated sources available, add the `build/generated-sources/jaxb` folder to the build path (right click on the `jaxb` folder and select "Build Path → Use as Source Folder").
- If you do not see the `build` folder in the `spring-oxm` project, ensure that the "Gradle build folder" is not filtered out from the view. This setting is available under "Filters" in the configuration of the Package Explorer (available by clicking on the _three vertical dots_ in the upper right corner of the Package Explorer).
1. Code away!
## Known Issues
1.`spring-core` and `spring-oxm` should be pre-compiled due to repackaged dependencies.
- See `*RepackJar` tasks in the build.
1.`spring-core` should be pre-compiled due to repackaged dependencies.
- See `*RepackJar` tasks in the `spring-core.gradle` build file.
1.`spring-oxm` should be pre-compiled due to JAXB types generated for tests.
- Note that executing `./gradlew :spring-oxm:check` as explained in the _Steps_ above will compile `spring-core` and generate JAXB types for `spring-oxm`.
1.`spring-aspects` does not compile due to references to aspect types unknown to Eclipse.
- If you installed _AJDT_ into Eclipse it should work.
1. While JUnit tests pass from the command line with Gradle, some may fail when run from
* Whether this environment lives within a native image.
* Exposed as a private static field rather than in a {@code NativeImageDetector.inNativeImage()} static method due to https://github.com/oracle/graal/issues/2594.
* Simple ClassFilter that looks for a specific Java 5 annotation
* being present on a class.
* Simple ClassFilter that looks for a specific annotation being present on a class.
*
* @author Juergen Hoeller
* @since 2.0
Some files were not shown because too many files have changed in this diff
Show More
Reference in New Issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.