Commit Graph

732 Commits

Author SHA1 Message Date
Sam Brannen 218a148898 Document null-safe index operator in SpEL
See gh-29847
2024-03-23 14:56:01 +01:00
Sam Brannen 38c473fd05 Support compilation of null-safe index operations in SpEL
See gh-29847
2024-03-23 13:48:20 +01:00
Sam Brannen d2bd0d5716 Retain null-safe syntax in AST representation of SpEL indexers
Prior to this commit, SpEL's CompoundExpression omitted the null-safe
syntax in AST string representations of indexing operations.

To address this, this commit implements isNullSafe() in Indexer.

See gh-29847
2024-03-23 12:46:03 +01:00
Sam Brannen 4d433174eb Revise null-safe index operator support in SpEL
See gh-29847
2024-03-23 12:46:03 +01:00
Grigory Stepanov 9f4d46fe33 Introduce null-safe index operator in SpEL
See gh-29847
2024-03-23 12:38:10 +01:00
Sam Brannen 2a1abb5553 Simplify compilation of array indexing in SpEL's Indexer 2024-03-23 12:35:25 +01:00
Sam Brannen 88bc3f270e Merge branch '6.1.x' 2024-03-22 17:18:38 +01:00
Sam Brannen 52b8c71dcd Retain null-safe syntax in AST representation of selection & projection
Prior to this commit, SpEL's CompoundExpression omitted the null-safe
syntax in AST string representations of the selection and projection
operators.

To address this, this commit implements isNullSafe() in Projection and
Selection.

Closes gh-32515
2024-03-22 17:05:48 +01:00
Sam Brannen b695dbc2bf Merge branch '6.1.x' 2024-03-22 16:37:55 +01:00
Sam Brannen f941754db6 Introduce isNullSafe() in SpelNodeImpl
Prior to this commit, MethodReference and PropertyOrFieldReference
already defined local isNullSafe() methods, but we need identical
methods in Selection, Projection, and Indexer, and we may potentially
need null-safe support for additional operators in the future.

To address the common need for an is-null-safe check, this commit
introduces an isNullSafe() method in SpelNodeImpl with a default
implementation that returns false.

Closes gh-32516
2024-03-22 16:37:08 +01:00
Sam Brannen d4495a5654 Revise PropertyOrFieldReference since isNullSafe() is not final 2024-03-22 16:37:08 +01:00
Sam Brannen 7f40b49f4d Improve names of classes generated by the SpEL compiler
Prior to this commit, the SpEL compiler generated classes in a package
named "spel" with names following the pattern "Ex#", where # was an
index starting with 2.

This resulted in class names such as:

- spel.Ex2
- spel.Ex3

This commit improves the names of classes created by the SpEL compiler
by generating classes in a package named
"org.springframework.expression.spel.generated" with names following
the pattern "CompiledExpression#####", where ##### is a 0-padded
counter starting with 00001.

This results in class names such as:

- org.springframework.expression.spel.generated.CompiledExpression00001
- org.springframework.expression.spel.generated.CompiledExpression00002

This commit also moves the saveGeneratedClassFile() method from
SpelCompilationCoverageTests to SpelCompiler and enhances it to:

- Save classes in a "build/generated-classes" directory.
- Convert package names to directories.
- Create missing parent directories.
- Use logging instead of System.out.println().

Running a test with saveGeneratedClassFile() enabled now logs something
similar to the following.

DEBUG o.s.e.s.s.SpelCompiler - Saving compiled SpEL expression [(#root.empty ? 0 : #root.size)] to [/Users/<username>/spring-framework/spring-expression/build/generated-classes/org/springframework/expression/spel/generated/CompiledExpression00001.class]

Closes gh-32497
2024-03-20 12:34:01 +01:00
Sébastien Deleuze f648fd7c3b Perform NullAway build-time checks in spring-expression
See gh-32475
2024-03-20 10:10:00 +01:00
Sébastien Deleuze 1ccd5512c5 Merge branch '6.1.x' 2024-03-20 10:08:30 +01:00
Sébastien Deleuze 2e98a8a2a4 Refine null-safety in spring-expression
See gh-32475
2024-03-20 10:07:56 +01:00
Juergen Hoeller e58ea0d945 Merge branch '6.1.x'
# Conflicts:
#	spring-core/src/main/java/org/springframework/core/CoroutinesUtils.java
2024-03-19 10:06:48 +01:00
Juergen Hoeller c531a8a705 Nullability refinements and related polishing
See gh-32475
2024-03-19 09:58:44 +01:00
Sam Brannen 38c831f15f Relocate findPublicDeclaringClass() to CodeFlow
This commit moves findPublicDeclaringClass() from ReflectionHelper to
CodeFlow, since findPublicDeclaringClass() is only used for bytecode
generation and therefore not for reflection-based invocations.
2024-03-11 11:33:52 +01:00
Sam Brannen b431594021 Make SpEL's OptimalPropertyAccessor private
It was never necessary for SpEL's OptimalPropertyAccessor to be public.

Instead, clients should interact with OptimalPropertyAccessor
exclusively via the CompilablePropertyAccessor API.

In light of that, this commit makes SpEL's OptimalPropertyAccessor
private.

Closes gh-32410
2024-03-10 20:38:19 +01:00
Sam Brannen 4c246b7c96 Consistently use canonical annotation names in string representations 2024-03-10 15:54:53 +01:00
Sam Brannen c188f22378 Polishing 2024-03-09 16:08:17 +01:00
Stéphane Nicoll e53ed3e3c6 Merge branch '6.1.x' 2024-03-09 16:03:04 +01:00
Stéphane Nicoll 4983a802a7 Polish "Fix Javadoc"
See gh-32403
2024-03-09 16:02:01 +01:00
Maksim Sasnouski abdccffa39 Fix Javadoc
This commit fixes various Javadoc issues across the code base.

See gh-32403
2024-03-09 16:02:00 +01:00
Sam Brannen f4c1ad7ae6 Polishing
See gh-29857
2024-03-09 15:38:52 +01:00
Sam Brannen 65d77624d1 Support SpEL compilation for public methods in private subtypes
Commit c79436f832 ensured that methods are invoked via a public
interface or public superclass when compiling Spring Expression
Language (SpEL) expressions involving method references or property
access (see MethodReference, PropertyOrFieldReference, and
collaborating support classes). However, compilation of expressions
that access properties by indexing into an object by property name is
still not properly supported in all scenarios.

To address those remaining use cases, this commit ensures that methods
are invoked via a public interface or public superclass when accessing
a property by indexing into an object by the property name – for
example, `person['name']` instead of `person.name`.

In addition, SpEL's Indexer now properly relies on the
CompilablePropertyAccessor abstraction instead of hard-coding support
for only OptimalPropertyAccessor. This greatly reduces the complexity
of the Indexer and simultaneously allows the Indexer to potentially
support other CompilablePropertyAccessor implementations.

Closes gh-29857
2024-03-09 14:01:00 +01:00
Sam Brannen 107f47cfcf Add tests for status quo for SpEL compiler 2024-03-09 13:46:39 +01:00
Sam Brannen 3577e3b758 Polish SpEL internals and tests 2024-03-08 17:49:58 +01:00
Sam Brannen 90867e7e62 Merge branch '6.1.x' 2024-03-08 15:50:29 +01:00
Sam Brannen fea1464562 Ensure SpEL can compile an expression indexing into a boolean array
Closes gh-32400
2024-03-08 15:32:57 +01:00
Sam Brannen c79436f832 Support SpEL compilation for public methods in private subtypes
Although the Spring Expression Language (SpEL) generally does a good
job of locating the public declaring class or interface on which to
invoke a method in a compiled expression, prior to this commit there
were still a few unsupported use cases.

To address those remaining use cases, this commit ensures that methods
are invoked via a public interface or public superclass whenever
possible when compiling SpEL expressions.

See gh-29857
2024-03-07 16:20:50 +01:00
Sam Brannen dcbc2ef134 Polishing 2024-03-07 13:55:35 +01:00
Sam Brannen 9eea768205 Polish SpEL internals 2024-03-06 11:31:10 +01:00
Sam Brannen 1fa6ac30b5 Remove unused lastReadInvokerPair field in ReflectivePropertyAccessor 2024-03-05 12:55:30 +01:00
Sam Brannen b44c31e997 Polishing 2024-03-05 12:01:55 +01:00
Sam Brannen 1ea593e777 Convert PropertyCacheKey to a record 2024-03-05 12:01:55 +01:00
Sam Brannen 70a545e13a Use appropriate variable names in ReflectivePropertyAccessor 2024-03-05 11:52:30 +01:00
Sam Brannen 4a6dbb17f4 Merge branch '6.1.x' 2024-03-03 14:51:01 +01:00
Sam Brannen 380184e85a Support SpEL compilation of #root or #this with non-public type
Prior to this commit, if a Spring Expression Language (SpEL) expression
referenced the root context object via the #root or #this variable, we
inserted a checkcast in the generated byte code that cast the object to
its concrete type. However if the root context object's type was
non-public, that resulted in an IllegalAccessError when the compiled
byte code was executed.

VariableReference.getValueInternal() already contains a solution for
global variables which inserts a checkcast to Object in the generated
byte code instead of to the object's concrete non-public type.

This commit therefore applies the same logic to #root (or #this when
used to reference the root context object) that is already applied to
global variables.

Closes gh-32356
2024-03-03 14:49:42 +01:00
Sam Brannen a29c84f663 Merge branch '6.1.x' 2024-03-02 18:08:27 +01:00
Sam Brannen 5cba32df32 Polish SpEL's VariableReference 2024-03-02 18:03:44 +01:00
Sam Brannen 11c40b5c1c Restructure SpEL indexer compilation tests 2024-03-02 18:03:44 +01:00
Sam Brannen fdbefad59c Improve documentation for SpEL indexing support
Prior to this commit, the reference manual only documented indexing
support for arrays, lists, and maps.

This commit improves the overall documentation for SpEL's property
navigation and indexing support and introduces additional documentation
for indexing into Strings and Objects.

Closes gh-32355
2024-03-01 18:08:29 +01:00
Sam Brannen 122372c580 Spring cleaning: update copyright headers 2024-02-23 12:21:22 +01:00
Sam Brannen 9c610d9a70 Spring cleaning: remove unnecessary semicolon 2024-02-23 12:21:22 +01:00
Sam Brannen 734fc476ee Polish SpEL's Indexer and test 2024-02-21 17:44:09 +01:00
Sam Brannen 5a2b127a21 SpEL's StringIndexingValueRef.isWritable() should return false 2024-02-21 17:36:46 +01:00
Sam Brannen d4cde29f75 Clean up TODOs in SpEL 2024-02-17 15:33:05 +01:00
Sam Brannen 5f1e25a61f Polishing 2024-02-17 15:32:43 +01:00
Sam Brannen eefdee7983 Fix syntax in Selection/Projection examples 2024-02-16 18:44:28 +01:00