I have been evaluating the support of Spring Boot 3 for native compiling with native-image
and so far I am very impressed. It has the potential to drastically reduce our cloud spend.
I note in the documentation, one of the major changes is the "closed world" assumption, meaning things like @ConditionalOn...
are evaluated at build time rather than compile time.
To give a common example, I have an EmailSender
interface and I have three implementations of this, for example LoggingEmailSender
, SmtpEmailSender
and SendGridEmailSender
. Currently when running on the JVM the correct Bean for the environment will be created, LoggingEmailSender
for local, SmtpEmailSender
for test and SendGridEmailSender
for production.
I am unsure what the best approach is to migrate this kind of conditional logic over to a Spring native way of doing things.
Currently the only option I can see would be to compile a binary per environment and use scopes at build and runtime to enable different implementations. This would result in a few different Docker images being created and deployed to their respective environments which breaks the previous conventions of promoting the same containers through various QA, Staging and then Production environments.
Is there a recommend strategy that I have overlooked or is this the best option available with the current level of maturity of native support?