Skip to content

Conversation

@cppwfs
Copy link
Contributor

@cppwfs cppwfs commented Nov 12, 2025

The Mail module documentation previously only showed XML configuration examples. This update adds examples for Java, Java DSL, Kotlin DSL, and Groovy DSL to help developers using these different configuration styles.

Changes include:

  • Outbound channel adapter configuration in all DSL flavors
  • Header enricher examples for all supported languages
  • Inbound adapters (both polling and IDLE) with DSL examples
  • JavaMail properties configuration examples
  • Search term strategy configuration examples
  • Mail filter expression examples across all DSL types
  • Transaction synchronization examples for all configurations
  • Minor typo fix in SearchTerm documentation
  • Minor grammar fixes

This makes the documentation more accessible to developers who prefer annotation-based or DSL configuration over XML.

Note:
In some cases there is no DSL for java, kotlin, or groovy. This is because the sample is for a supporting bean of the DSL vs. the DSL itself.

@cppwfs cppwfs requested a review from artembilan November 12, 2025 18:08
@artembilan artembilan added this to the 7.0.0 milestone Nov 12, 2025
Copy link
Member

@artembilan artembilan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is right direction.
Thank for such a thorough rework!
Sorry for a lengthy review.

return new MailToStringTransformer();
}
...
.transform(Mail.toStringTransformer())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just minor: there is no need in period for Kotlin/Groovy DSLs.
See examples in the KotlinDslTests and GroovyDslTests, respectively.
😄

@ServiceActivator(inputChannel = "outboundMail")
public MessageHandler outboundMailMessageHandler(JavaMailSender mailSender) {
MailSendingMessageHandler handler = new MailSendingMessageHandler(mailSender);
return handler;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit-pick: no need in local variable if we don't use it.
Just return new MailSendingMessageHandler(mailSender)`.

fun mailOutboundFlow(mailSender: JavaMailSender): IntegrationFlow {
return IntegrationFlow.from("outboundMail")
.handle(Mail.outboundAdapter(mailSender))
.get()
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not Kotlin idiomatic style.
Let me know if you'd like to pair on these samples!
Neither Groovy bellow.

[[configuring-outbound-channel-adapters]]
== Configuring Outbound Channel Adapters

To configure an outbound channel adapter, provide the channel from which to receive and the MailSender, as the following example shows:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The MailSender must be a code snippet.

======

Alternatively, you can provide the host, username, and password, as the following example shows:
Alternatively, you can configure the mail sender directly with host credentials:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well, this is a bit confusing.
Samples above show a JavaMailSender injection, but is there its definition?

fun imapMailReceiver(): ImapMailReceiver {
return ImapMailReceiver("imap:something").apply {
// ...
setSearchTermStrategy(TestSearchTermStrategy())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is an instantiation of the TestSearchTermStrategy directly.
While all other samples talk about an injection into bean method.

Spring Integration 2.0.4 introduced the `mail-filter-expression` attribute on `inbound-channel-adapter` and `imap-idle-channel-adapter`.
This attribute lets you provide an expression that is a combination of SpEL and a regular expression.
For example, if you would like to read-only emails that contain 'Spring Integration' in the subject line, you would configure the `mail-filter-expression` attribute like as follows: `mail-filter-expression="subject matches '(?i).\*Spring Integration.*"`.
For example, if you would like to read only emails that contain 'Spring Integration' in the subject line, you would configure the `mail-filter-expression` attribute like as follows: `mail-filter-expression="subject matches '(?i).\*Spring Integration.*"`.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think this is correct fix.
read only and read-only have a different meaning and reads differently.

You can enable transaction synchronization by adding a `<transactional/>` element to the poller for the polled `<inbound-adapter/>` or to the `<imap-idle-inbound-adapter/>`.
When using XML schema, transaction synchronization is enabled by adding a `<transactional/>` element to the poller for the polled `<inbound-adapter/>` or to the `<imap-idle-inbound-adapter/>`.
Even if there is no 'real' transaction involved, you can still enable this feature by using a `PseudoTransactionManager` with the `<transactional/>` element.
When using Java configuration you can establish the transaction synchronization by using the `transactionSynchronizationFactory(transactionSynchronizationFactory)` method on the `PollerMetadata` or via the DSL.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think a comma is supposed to be after the first part of the sentence when it starts with when, if, because.
My English is not the best, but still some rules are in my head 😄

----
@Bean
public IntegrationFlow imapIdleFlow(ImapMailReceiver imapMailReceiver, MessageChannel receiveChannel,
MailMessageHandler mailMessageHandler) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is no such a class in the Framework.
And I don't think we need to mention anything here at all.
See XML sample this was derived from.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Artifact of Proofs. Apologies.

)
}
return IntegrationFlow
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Kotlin DSL sample needs more work.
And ExpressionEvaluatingTransactionSynchronizationProcessor has to be a bean.

Copy link
Member

@artembilan artembilan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That is great!
Let's talk about Groovy then tomorrow!
Thank you!

The Mail module documentation previously only showed XML configuration
examples. This update adds examples for Java, Java DSL, Kotlin DSL,
and Groovy DSL to help developers using these different configuration
styles.

Changes include:
- Outbound channel adapter configuration in all DSL flavors
- Header enricher examples for all supported languages
- Inbound adapters (both polling and IDLE) with DSL examples
- JavaMail properties configuration examples
- Search term strategy configuration examples
- Mail filter expression examples across all DSL types
- Transaction synchronization examples for all configurations
- Minor typo fix in SearchTerm documentation
- Minor grammar fixes

This makes the documentation more accessible to developers who prefer
annotation-based or DSL configuration over XML.

Note:
In some cases there is no DSL for java, kotlin, or groovy.
This is because the sample is for a supporting bean of the DSL vs. the DSL itself.
Code example changes:

- Expand outbound adapter examples to show complete `JavaMailSender`
  bean configuration for Java, Java DSL, Kotlin DSL, and Groovy DSL
- Simplify Java examples by inlining return statements
- Add duplicate Groovy DSL example showing both credential styles
- Restructure IMAP idle adapter examples to use inline URI
  configuration instead of separate receiver bean creation
- Remove complete mail flow examples from header enricher section,
  keeping only enrichment examples
- Modify Kotlin DSL examples to use different patterns (`integrationFlow`
  function vs `IntegrationFlow.from()`)
- Update Groovy Properties construction to use map constructor syntax
- Simplify Kotlin `imapMailInboundFlow` to remove explicit return type
- Replace phrasing around terms as "you" and "we"
- Groovy samples were updated but are not idiomatic of the language.  Request assistance
Update Groovy code examples in mail.adoc to follow idiomatic Groovy
patterns, remove Java-style verbosity, and fix syntax errors
introduced in previous commits. Changes include:

- Replace `IntegrationFlow.from().get()` with `integrationFlow {}` DSL
- Use `.with {}` builder pattern for adapter configuration
- Apply property-style setters (`shouldDeleteMessages true`)
- Remove explicit return types leveraging Groovy type inference
- Restore essential poller configuration for inbound adapters
- Use consistent property assignment style throughout examples
Copy link
Member

@artembilan artembilan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM.
Pulling locally for final review and possible clean up.
Thank you!

@artembilan
Copy link
Member

Merged as 14f72bd after some minor fixes.
Thank you again!

@artembilan artembilan closed this Nov 18, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants