cloudfoundry / java-buildpack

Cloud Foundry buildpack for running Java applications
Apache License 2.0
436 stars 2.58k forks source link

Spring Auto Reconfiguration & Spring Cloud Connectors Deprecation Notice #951

Open dmikusa opened 2 years ago

dmikusa commented 2 years ago

As was communicated on Slack, Github, and now with the latest Java Buildpack Release Notes (v4.49). Support for the Spring Auto Reconfiguration and Spring Cloud Connectors has been deprecated.

The buildpack will start by warning all users that have these features enabled. After Aug 2022, the buildpack will default to disabling these features and it will require users to explicitly opt into using them. After Dec 2022, all support for them will be removed.

The path forward is to use java-cfenv in your application. There CloudFoundry docs have instructions & migration information for users coming from Spring Cloud Connectors & Auto Reconfiguration.

This issue has been opened as an announcement and as a location for users to post feedback. Please feel free to post comments below or on Slack.

coffee-squirrel commented 2 years ago

FYI-- we've had a couple teams get bitten by the following:

We've advised them of how to fix the immediate issue (explicitly include cloud when deploying), and this behavior is mentioned in the migration guide, but going solely off of the v4.49 release notes one could reasonably assume no change in behavior until August 2022.

dmikusa commented 2 years ago

Thanks @coffee-squirrel, you're 100% correct that I missed that change in the release notes. Apologies. I have updated the release notes to mention the feature change and to also bring more attention to the fact that the cloud profile needs to be manually enabled going forward.

Hopefully that will help with folks performing the migration going forward.

pivotal-david-osullivan commented 1 year ago

Just an update on this issue - we are extending the deprecation period until 2023/2024. This will give users more time to follow the migration guide and switch to java-cfenv.

Starting with the next release, Spring Auto Reconfiguration will be enabled by default as it was up to 4.51 and warnings will continue to be logged if the library is injected by the buildpack. The buildpack will default to disabling these features after the new date of March 2023 (explicit opt-in still possible), with the removal planned for a release after March 2024.

andrewpolemeni commented 1 year ago

Could we possibly enhance the documentation? Like a 1-to-1 comparison of old vs new with examples. Maybe a sample spring boot application to show what's changed. Not sure if I need to add that CfEnv bean and replace my vcap properties with cfEnv.findCredentialsByTag. A good example of how to make the docs better would be:

REMOVED | REPLACEMENT | DETAILS -- | -- | -- REMOVED | REPLACEMENT | Explain why it's been removed.
dmarmugi commented 1 year ago

The buildpack will default to disabling these features after the new date of March 2023

I haven't seen this in the release notes -- did this happen or has the date slipped? Is there a new target date?

dmarmugi commented 10 months ago

Hi, the v4.62.0 Release Notes state:

... This release adds a new framework, java_cf_env which supplies the Java CfEnv library to Spring Boot 3 apps, instead of the deprecated Spring AutoReconfiguration library.

Spring Boot 2 apps will continue to receive the Spring AutoReconfiguration library for the life of Spring Boot 2.x, whereas Spring Boot 3 users will now receive Java CfEnv as an app dependency...

This conflicts with what was stated in this issue:

...all support for them will be removed...

Is my understanding correct that the v4.62.0 buildpack release and its described deprecation timeline supersedes this one?

dev-praveen commented 7 months ago

We have a spring boot application (version 1.5.9.RELEASE) that is deployed in PCF and works fine. We are trying to migrate it to java-cfenv-boot library by following the migration guide and removing the dependencies it suggests. However, we encounter a problem with the centralized configuration. The application fails to get the placeholder values from the Spring Cloud Config Server (bound to PCF). This is the error we get: [OUT] Caused by: java.lang.IllegalArgumentException: Could not resolve placeholder ‘some.value’ in value “${some.value}”

removed org.springframework.boot:spring-boot-starter-cloud-connectors or org.springframework.cloud:spring-cloud-core org.springframework.cloud:spring-cloud-connectors-core org.springframework.cloud:spring-cloud-cloudfoundry-connector org.springframework.cloud:spring-cloud-spring-service-connector dependencies from pom file

added

io.pivotal.cfenv java-cfenv-boot 2.4.0
spring.profiles.active: dev,cloud
JBP_CONFIG_SPRING_AUTO_RECONFIGURATION: '{enabled: false}'

and we use java_buildpack_offline Please suggest to fix the issue.

anthonydahanne commented 7 months ago

hello @dev-praveen ! Unfortunately, you don't provide a lot of details (no logs nor manifest for your spring app deployment in Tanzu Application Service) and you refer to a Spring Boot version that was deprecated... 3 years ago... I'd suggest you migrate to latest supported spring boot version and retry

dev-praveen commented 7 months ago

@anthonydahanne thanks for the reply below is manifest file and logs.

applications:

2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'callbackServiceNavigator': Unsatisfied dependency expressed through field 'applicationThreadPoolExecutor'; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'scopedTarget.springAsyncConfig': Injection of autowired dependencies failed; nested exception is java.lang.IllegalArgumentException: Could not resolve placeholder 'threadpool.corepool.size' in value "${threadpool.corepool.size}" 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:588) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:761) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:867) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:543) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:122) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:693) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:360) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.SpringApplication.run(SpringApplication.java:303) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.SpringApplication.run(SpringApplication.java:1118) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.SpringApplication.run(SpringApplication.java:1107) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at com.telstra.asset.service.migration.TRAMASApplication.main(TRAMASApplication.java:37) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at java.lang.reflect.Method.invoke(Method.java:498) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.loader.MainMethodRunner.run(MainMethodRunner.java:48) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.loader.Launcher.launch(Launcher.java:87) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.loader.Launcher.launch(Launcher.java:50) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.boot.loader.JarLauncher.main(JarLauncher.java:51) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'scopedTarget.springAsyncConfig': Injection of autowired dependencies failed; nested exception is java.lang.IllegalArgumentException: Could not resolve placeholder 'threadpool.corepool.size' in value "${threadpool.corepool.size}" 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:372) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory$2.getObject(AbstractBeanFactory.java:345) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.cloud.context.scope.GenericScope$BeanLifecycleWrapper.getBean(GenericScope.java:359) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.cloud.context.scope.GenericScope.get(GenericScope.java:176) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:340) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:372) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1173) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1067) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:513) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:208) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1138) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] ... 27 common frames omitted 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] Caused by: java.lang.IllegalArgumentException: Could not resolve placeholder 'threadpool.corepool.size' in value "${threadpool.corepool.size}" 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.util.PropertyPlaceholderHelper.parseStringValue(PropertyPlaceholderHelper.java:174) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.util.PropertyPlaceholderHelper.replacePlaceholders(PropertyPlaceholderHelper.java:126) 2024-01-29T12:02:58.633+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.core.env.AbstractPropertyResolver.doResolvePlaceholders(AbstractPropertyResolver.java:236) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.core.env.AbstractPropertyResolver.resolveRequiredPlaceholders(AbstractPropertyResolver.java:210) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.context.support.PropertySourcesPlaceholderConfigurer$2.resolveStringValue(PropertySourcesPlaceholderConfigurer.java:172) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.AbstractBeanFactory.resolveEmbeddedValue(AbstractBeanFactory.java:831) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1086) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366) 2024-01-29T12:02:58.634+05:30 [APP/PROC/WEB/0] [OUT] ... 48 common frames omitted 2024-01-29T12:02:58.973+05:30 [APP/PROC/WEB/0] [OUT] Exit status 1

dev-praveen commented 7 months ago

Hi Few more observations to the previous one, after removing

org.springframework.boot:spring-boot-starter-cloud-connectors or org.springframework.cloud:spring-cloud-core org.springframework.cloud:spring-cloud-connectors-core org.springframework.cloud:spring-cloud-cloudfoundry-connector org.springframework.cloud:spring-cloud-spring-service-connector

dependencies from the project. Application couldn't able to locate the real config server and it is fall back to localhost 024-02-08T17:22:22.762+05:30 [APP/PROC/WEB/0] [OUT] 2024-02-08 11:52:22.761 INFO 8 --- [ main] c.c.c.ConfigServicePropertySourceLocator : Fetching config from server at: http://localhost:8888 2024-02-08T17:22:22.892+05:30 [APP/PROC/WEB/0] [OUT] 2024-02-08 11:52:22.892 WARN 8 --- [ main] c.c.c.ConfigServicePropertySourceLocator : Could not locate PropertySource: I/O error on GET request for "http://localhost:8888/application/dev,cloud": Connection refused (Connection refused); nested exception is java.net.ConnectException: Connection refused (Connection refused) 2024-02-08T17:22:22.895+05:30 [APP/PROC/WEB/0] [OUT] 2024-02-08 11:52:22.895 INFO 8 --- [ main] c.t.a.s.migration.Application : The following profiles are active: dev,cloud

with the above dependencies in the project belwo are the logs:

2024-01-25T12:52:52.305+05:30 [APP/PROC/WEB/0] [OUT] 2024-01-25 07:22:52.305 INFO 7 --- [ main] c.c.c.ConfigServicePropertySourceLocator : Fetching config from server at: https://config-server-11121121a-fdec-4ba5-c654-5ccff667744.apps.np.app.com

2024-01-25T12:52:54.122+05:30 [APP/PROC/WEB/0] [OUT] 2024-01-25 07:22:54.122 INFO 7 --- [ main] b.c.PropertySourceBootstrapConfiguration : Located property source: CompositePropertySource [name='configService', propertySources=[MapPropertySource {name='credhub-app-dev-master'}, MapPropertySource {name='credhub-app-dev-master'}, MapPropertySource {name='ssh://mirror@10.100.100.8:22/var/vcap/store/mirror/8475euhfjy348573857rjhgdfjh745647/davinci-config/davinci-app-dev.properties'}, MapPropertySource {name='ssh://mirror@10.100.100.8:22/var/vcap/store/mirror/8475euhfjy348573857rjhgdfjh745647/davinci-config/application.properties'}]]

please help us why after removing recommended dependencies from the documentation application is not able to locate the real config server.

dev-praveen commented 6 months ago

I would like to request the community to extend the timeline for disabling the spring auto reconfiguration feature that comes with the java_buildpack_offline.

nmck257 commented 4 days ago

Hi - the timeline described in this warning message seems a bit stale; can we confirm the latest plan?

https://github.com/cloudfoundry/java-buildpack/blob/e2dd4eb641fd14b9978b1a714d7bcbf9b9a2ce00/lib/java_buildpack/framework/spring_auto_reconfiguration.rb#L96-L100

anthonydahanne commented 4 days ago

@nmck257 - true. The (auto injected jars) reality currently is :

of course, those "auto" behaviors can be disabled via either JBP_CONFIG_SPRING_AUTO_RECONFIGURATION='{enabled: false}' and / or JBP_CONFIG_JAVA_CF_ENV='{enabled: false}'

nmck257 commented 4 days ago

that helps -- so to further clarify:

anthonydahanne commented 4 days ago

SAR/SCC injection have not (yet) been switched to default-disabled, like the message would have implied?

that's correct; we found out many users were not ready to have this default behavior removed.

is there any imminent plan to drop SAR/SCC support?

No

Or at this point are we planning to keep it around as long as SB 2 support is kept around?

Yes