Parts were emitted only from PartListener.onBody(buffer, last=true), so a
part with an empty body (for example a blank form field, or a trailing
empty part) was silently dropped from the resulting MultiValueMap, and
was indistinguishable from an absent field.
This carries over the fix from the reactive DefaultPartHttpMessageReader
(spring-framework#30953): State gains an onComplete() callback that emits
the part, also when it has an empty body. It is invoked when a new part
begins, and when parsing completes for the final part.
Signed-off-by: Sagar Chanchal <Sagarr2112@gmail.com>
When a column was declared via usingColumns() and also listed in
usingGeneratedKeyColumns(), TableMetaDataContext.reconcileColumnsToUse
accepted the declared list as-is: the generated key column was rendered
into the INSERT statement and counted against the parameter values,
even though the database is expected to generate its value.
Such an overlap is a configuration error, so it is now rejected at
compile time with an InvalidDataAccessApiUsageException naming the
offending columns in their declared spelling, consistent with the
existing validation in AbstractJdbcInsert.compile(). Matching is
case-insensitive, mirroring the normalization used for auto-discovered
columns; the auto-discovery path itself is unchanged and continues to
exclude generated key columns silently.
The tests cover the rejection, its message, a case-insensitive variant,
and the untouched non-overlapping declared path.
Closes gh-37014
Signed-off-by: junhyeong9812 <pickjog@gmail.com>
This commit makes use of the Java specification version in the Jar
metadata to make build easier to reproduce on a different environment.
Closes gh-37250
This commit adds the missing reflection hints for Hibernate 8 support:
`PersistenceUnitInfoDescriptor` and `StatelessSession`.
Fixes gh-37247
Fixes gh-37249
Every error code setter in SQLErrorCodes sorts its array with
StringUtils.sortStringArray, and CustomSQLErrorCodesTranslation does
the same, because SQLErrorCodeSQLExceptionTranslator looks the codes
up with Arrays.binarySearch. setDuplicateKeyCodes was the only setter
that stored the supplied array as-is.
With an unsorted list of duplicate key codes, the binary search finds
or misses a code depending on where the values happen to sit: for
codes it misses, the translator silently falls through to the SQLState
fallback and reports a DataIntegrityViolationException, or fails to
translate at all, instead of the configured DuplicateKeyException. The
default sql-error-codes.xml is not affected since its lists are
already sorted; the mismatch surfaces for custom configurations, for
example codes of different digit lengths listed in numeric order.
setDuplicateKeyCodes now sorts the array like all sibling setters. The
new test covers an unsorted custom list whose codes previously hit or
missed depending on their position.
Closes gh-37235
Signed-off-by: junhyeong9812 <pickjog@gmail.com>
Migrate RequestMappingHandlerAdapterTests#responseBodyAdvice from the
deprecated MappingJackson2HttpMessageConverter to
JacksonJsonHttpMessageConverter.
The test advice now implements ResponseBodyAdvice directly and returns a
map body that is written by the selected converter.
This maintains the test coverage for gh-22638, verifying that a
ControllerAdvice implementing both ResponseBodyAdvice and
RequestBodyAdvice is not registered twice.
Signed-off-by: Sunghyun Shin <froggy0m0a@gmail.com>
PrimitiveDelegate generated code via "$LF" for Float and "(double) $L"
for Double, which emit the value's toString() verbatim. For NaN and
infinities this produced non-compilable source such as "NaNF" or
"(double) Infinity", causing the generated AOT sources to fail to
compile.
Detect NaN (via isNaN, since NaN is never equal to itself) and the
positive/negative infinities, emitting the corresponding constant
field references (Float.NaN, Double.POSITIVE_INFINITY, etc.) through
the "$T" placeholder. Finite values keep their existing handling.
Signed-off-by: junhyeong9812 <pickjog@gmail.com>
GeneratedClass.reserveMethodNames(String...) passed the entire varargs
array to MethodName.of() inside the per-name loop instead of the current
element. Since MethodName.of(String...) joins all parts into a single
camel-case name, reserving two or more names (for example "apply" and
"test") produced "applyTest", and the per-element check
Assert.state(generatedName.equals(reservedMethodName)) failed with an
IllegalStateException. Single-name calls worked only by accident.
Reserve each supplied name individually by passing the loop variable.
Signed-off-by: junhyeong9812 <pickjog@gmail.com>
Prior to this commit, AbstractBrokerMessageHandler logged the
BrokerAvailabilityEvent object directly at INFO level. With a structured
JSON logging layout, the event could be serialized as an object rather
than via toString(), causing the layout to traverse the event source
(a SimpleBrokerMessageHandler) object graph. That graph contains a
cyclic reference through the client inbound channel executor's thread
factory, which fails serialization at the maximum nesting depth.
This commit logs the event's toString() representation instead, keeping
the same operational signal while preventing structured logging layouts
from traversing framework internals.
Signed-off-by: kodacme <kodac.saito@kodac.me>
Prior to this commit, SSE support in Spring would write payloads with
the "data:" prefix (without space). While this is OK with the standard,
this makes it harder for implementations to support reading and writing
payloads with Spring (the round trip use case).
This commit introduces a breaking change and now enforces "data: " in
all variants. This has the potential of breaking some low level test
suites with text/plain or custom media types, but this should overall
make the situation better for developers.
Closes gh-37242
Narrow the scope of the @SuppressWarnings("NullAway") annotation in
DateTimeFormatterRegistrar from the class level to a single, new
getFactory(Type) accessor.
The `factories` map is a private, final EnumMap that is fully populated
for every `Type` in the constructor and never mutated afterward, so the
suppression only needs to cover that one lookup instead of masking
unrelated issues across the whole class.
Closes gh-37225
Signed-off-by: Junhwan Choi <devjunsday@gmail.com>C
Prior to this commit, AbstractXMLStreamReader.getTextCharacters(int
sourceStart, char[], int, int) capped the copy length with
Math.min(length, source.length), ignoring sourceStart. When sourceStart
> 0 and sourceStart + length exceeds the text length, System.arraycopy
read past the end of the source array and threw
ArrayIndexOutOfBoundsException, contrary to the
XMLStreamReader#getTextCharacters contract (copy up to length
characters starting at sourceStart and return the number copied).
To address that, this commit caps the length by the number of
characters remaining from sourceStart.
Closes gh-36914
Signed-off-by: junhyeong9812 <pickjog@gmail.com>
The static SimpleDateFormat instance in
AbstractMockHttpServletRequestBuilder is shared across all
instances. SimpleDateFormat.format() mutates internal Calendar
state and is not thread-safe, which can produce corrupt date
strings or ArrayIndexOutOfBoundsException when tests run in
parallel.
Replace with DateTimeFormatter which is immutable and thread-safe.
Signed-off-by: Sebastien Tardif <SebTardif@ncf.ca>
RFC 9651 specifies @«timestamp» as a new format for date headers.
The Deprecation header as specified in RFC 9745, for example, makes use of it.
Make sure this can be parsed using `HttpHeaders#getFirstDate` and `HttpHeaders#getFirstZonedDateTime`
Signed-off-by: Raphael Schweikert <any@sabberworm.com>
Gradle 9.6 deprecates passing a Project instance as dependency notation,
which currently causes the build to emit deprecation warnings and will
become an error in Gradle 10.
This commit updates KotlinConventions and RuntimeHintsAgentPlugin to use
DependencyFactory#createProjectDependency instead.
Signed-off-by: Hyunwoo Jung <hyunwoojung@kakao.com>
The new PartGenerator for parsing multipart requests supports buffering
the content in memory and switching to a file after a configured size.
More specifically, when a multipart part exceeds maxInMemorySize and
InMemoryState switches it over to FileState, the bytes that were
already buffered in memory are flushed to the temp file.
Prior to this commit, this was done via FileState.writeBuffer(), meaning
that the in memory buffered data would not be counted against the
configured limit for writing to a file.
This commit fixes this by writing buffered data with FileState.onBody().
Fixes gh-37238