Skip to content

Add symbol processor for configuration metadata - #51375

Closed
salatmaster wants to merge 3 commits into
spring-projects:mainfrom
salatmaster:gh-28046-ksp-configuration-processor
Closed

salatmaster wants to merge 3 commits into
spring-projects:mainfrom
salatmaster:gh-28046-ksp-configuration-processor

Conversation

@salatmaster

Copy link
Copy Markdown

This adds spring-boot-configuration-symbol-processor, a KSP processor that generates configuration metadata for Kotlin sources, as an alternative to running the annotation processor through kapt. It reuses the metadata model of the existing annotation processor, so the generated META-INF/spring-configuration-metadata.json is identical in format.

Besides removing the need for kapt, it fixes metadata that kapt currently loses. For a data class with Kotlin defaults:

@ConfigurationProperties("demo")
data class DemoProperties(val port: Int = 8080, val name: String = "demo")

kapt generates a stub with two constructors, the annotation processor can no longer deduce the bind constructor, and no properties end up in the metadata at all — only the group. The symbol processor describes both properties. KDoc on constructor parameters (@property) is picked up as well, which kapt drops.

Supported: constructor and JavaBean binding, @DefaultValue, @Name, nested groups, @NestedConfigurationProperty, @ConfigurationProperties on a method, actuator endpoints, deprecations, KDoc descriptions, merging of additional-spring-configuration-metadata.json, and @ConfigurationPropertiesSource.

Known limitations, all covered in the new appendix section:

  • Default values declared with an initializer are invisible to KSP ([feature request] Retrieve property default value for compile time constants google/ksp#1868). kapt does not expose them either, so this is not a regression, and @DefaultValue still works.
  • Additional metadata has to be located with a processor option, since KSP gives a processor no access to module resources.
  • A module has to apply either this processor or the annotation processor, as both write the same file.
  • Endpoint annotations are matched directly rather than through meta-annotations.

Tests drive the processor through the KSP2 API directly, so there is no third-party test dependency. The processor is compiled against symbol-processing-api 2.3.0 and declares it as compileOnly, so the KSP version stays under the user's control.

I'm aware this is marked as pending design work, so please treat it as a concrete proposal rather than a finished feature — happy to rework it if you'd rather see a different shape, such as an abstraction shared with the annotation processor.

See gh-28046

@spring-projects-issues spring-projects-issues added the status: waiting-for-triage An issue we've not yet triaged label Aug 12, 2026
@salatmaster
salatmaster force-pushed the gh-28046-ksp-configuration-processor branch from ae9a47e to 60d3b03 Compare August 12, 2026 14:07
Add spring-boot-configuration-symbol-processor, a Kotlin Symbol
Processing (KSP) processor that writes the configuration metadata of
Kotlin types. It reuses the metadata model of the annotation processor,
so the generated META-INF/spring-configuration-metadata.json is
identical in format, and it lets a Kotlin project generate its metadata
without kapt.

The processor supports constructor binding and JavaBean binding, nested
groups, @ConfigurationProperties on a method, actuator endpoints,
descriptions taken from KDoc, deprecations, and the merging of
META-INF/additional-spring-configuration-metadata.json. A type annotated
with @ConfigurationPropertiesSource is described in a file of its own.

Kotlin types are reported using their JVM names, so that a List<String>
property is described as java.util.List<java.lang.String> as it is when
the annotation processor runs.

See spring-projectsgh-28046

Signed-off-by: Areg Iazychian <abstractcoderx@gmail.com>
Add the symbol processor to spring-boot-dependencies so that a project
can declare it without having to specify its version.

See spring-projectsgh-28046

Signed-off-by: Areg Iazychian <abstractcoderx@gmail.com>
Describe how to apply the symbol processor, the types that it supports,
how to contribute additional metadata, and its limitations. Note that a
module has to apply either the annotation processor or the symbol
processor, as both write the same metadata file.

See spring-projectsgh-28046

Signed-off-by: Areg Iazychian <abstractcoderx@gmail.com>
@salatmaster
salatmaster force-pushed the gh-28046-ksp-configuration-processor branch from 60d3b03 to 86bbb93 Compare August 12, 2026 14:09
@philwebb philwebb added the for: team-meeting An issue we'd like to discuss as a team to make progress label Aug 26, 2026
@wilkinsona

wilkinsona commented Sep 2, 2026 •

Copy link
Copy Markdown
Member

Thanks for the proposal. Unfortunately, we're not happy with the approach taken here as it duplicates a considerable amount of logic between the Java annotation processor and the proposed KSP support. Ideally, any KSP support should be as thin a layer as possible that deals with Kotlin specifics before delegating to an implementation written in Java that's shared between the Java annotation processor and the KSP support. The issue is pending design work as we don't know exactly how to do that or if it's even feasible. If it proves not to be feasible it's unlikely that we'll support KSP as the maintenance burden will be too great.

@wilkinsona wilkinsona closed this Sep 2, 2026
@wilkinsona wilkinsona added status: declined A suggestion or change that we don't feel we should currently apply and removed status: waiting-for-triage An issue we've not yet triaged for: team-meeting An issue we'd like to discuss as a team to make progress labels Sep 2, 2026
@wilkinsona

Copy link
Copy Markdown
Member

happy to rework it if you'd rather see a different shape, such as an abstraction shared with the annotation processor

Just noticed this after I'd made the previous comment.

This is exactly what we'd prefer to see. If you'd like to make an alternative proposal that takes this approach, or explore its feasibility and comment on the issue with your findings, that would be great.

@salatmaster

Copy link
Copy Markdown
Author

Thanks for the feedback, @wilkinsona. I've explored the approach that you described and opened #51930 as an alternative proposal.

It introduces a small language-neutral model in spring-boot-configuration-processor and moves the logic of the annotation processor onto it, so that the annotation processor and the KSP support are two thin adapters over the same Java implementation. The KSP side no longer contains any metadata logic, and the metadata that the annotation processor generates for Spring Boot's own modules is unchanged. The details and what I'd like your opinion on are in the description of the new pull request.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

status: declined A suggestion or change that we don't feel we should currently apply

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants