Datasource creation failed using PCF User Provided Service - java

I have a SpringBoot application and deploying it in PCF where app is trying to connect Oracle 12c Database using PCF User Provided Services but it failing with this error Failed to determine a suitable driver class
build.gradle code:
and here are the configuration that I used in CUP service:
Service binding is happening properly. I can see the same details under VCAP_SERVICES in Environment Variables.
Error:

Short Answer: I think you want the uri to be oracle://... Strip off the jdbc: part. The Spring Autoreconfiguration code that gets injected by the Java buildpack will look at the prefix on the URI, so it needs oracle:// to know it's an Oracle link.
Long Answer: You probably don't want to depend on the injected Spring Autoreconfiguration. When it just works, it's great, but it can be difficult to understand what it's doing when it doesn't work.
It is better to use Spring Cloud Connector or even better, as all signs point to this replacing Spring Cloud Connector, use java-cfenv. For details on java-cfenv, see this blog post.
Spring Cloud Connector has the same issue I mentioned above as the Spring Autoreconfiguration, except that it will pretty clearly tell you when it doesn't recognize a bound service. Anyway, if you decide to use SCC, make sure you prefix the URI with oracle://.
If you use java-cfenv, it's more flexible so it's really up to you what properties and values you inject through the service.
Hope that helps!

Related

How do I connect to multiple databases/instances in GCP Spanner using Spring Cloud GCP Starter?

I am currently building an application that connects to a database on Spanner. The end goal of the application is to be able to connect to multiple databases (and possibly instances) so it can pull data using a GraphQL implementation. I am currently using Spring Cloud GCP Starter and Spring Cloud GCP Starter Data Spanner Maven packages to handle the configuration and data mapping. The Spring Cloud GCP Starter asks me to set up these lines in application.properties:
spring.cloud.gcp.spanner.instance-id=blah
spring.cloud.gcp.spanner.database=blah
spring.cloud.gcp.project-id=blah
Currently the application is set up to have models for each table, a repository (using SpannerRepository), and a controller.
The issue is I haven't been able to figure out how to change the configuration from the initial values when the application is run. Has anyone run into this and figured it out, or is it a limitation of my current implementation in Spring Cloud GCP Starter and I should look for different solution?
What I have tried:
Tried finding someone with the same issue online, nothing similar that I can find currently
Tried looking how to use/change the low level implementations things like SpannerTemplate that the autoconfiguration creates, but wasn't able to figure out how to change/use them
Tried finding a way to change application.properties and reloading during runtime, but after some research this seemed like a horrible idea
Any help would be greatly appreciated, thank you!
I finally found it!
Documentation
By creating a custom bean for DatabaseIdProvider you can set the projectId, instanceId, and database to whatever you would like. Confirmed to be working the SpannerRepository implementation as well.
If anyone else finds this, here is an example of how you would create your own implementation (how you go about feeding it a new database name is up to you):
#Bean
public DatabaseIdProvider databaseIdProvider() {
return () -> DatabaseId.of("projectId", "instanceId", "databaseName");
}
The DatabaseIdProvider interface extends Supplier<DatabaseId>. DatabaseId has a method (of) that creates the new DatabaseId that you need to connect to a different database/instance.

Camel Salesforce Kafka Source Connector does not start

I am trying to run the Camel Salesforce Kafka Source Connector version 1.0.x (LTS) and following the documentation as described on https://camel.apache.org/camel-kafka-connector/1.0.x/reference/connectors/camel-salesforce-source-kafka-source-connector.html all I need to do is to configure a bunch of camel.kamelet.salesforce-source.xxx properties which is exactly what I did.
Let's just assume that camel.kamelet.salesforce-source.clientId=xyz
When trying to run the connector it fails to start complaining that clientId is an unknown parameter:
Failed to resolve endpoint: salesforce://event/Case__e?clientId=xyz due to:
There are 1 parameters that couldn't be set on the endpoint.
Check the uri if the parameters are spelt correctly and that they are properties of the endpoint.
Unknown parameters=[{clientId=xyz}]
Running out of ideas I tried to configure a camel route myself and specified the clientId part of the salesforce endpoint. The issue was exactly the same. Running out of ideas I asked this question Unable to create camel salesforce endpoint and got a valid explanation for that behaviour: This type of settings should be done at component level not at endpoint level.
Digging further I checked that version 0.11.x (LTS) allows us to configure camel.component.salesforce.xxx properties as opposed to 1.0.x (LTS) which only has camel.kamelet.salesforce-source.xxx. In fact I was able to start the 0.11.x (LTS) connector.
Now it is hard to believe the migration from 0.11.x to 1.0.x was not fully tested and I am tempted to say I am missing some basic setup.
Can anyone bring some light in here?
Thank you in advance for your inputs.

Testing Application code local while using k8s for for the deployment of app

We are using k8s for deploying our application and it works awesome.But there is a small issue.We have moved from http layer communication to tcp layer.And the communication between different micro-services is through the service (k8s service) name and it works great but the developer can't test the same code locally as the service name will be resolved inside the cluster only.So here are some solutions that I have :-
1.Provided them a different name space where they can test the app with small changes.
The issue with this is that the developers use some break points and test some small changes in code and debug that will be hard by this method.
2.They can implement minikube in local but that doesn't sound good to even me.
3.They can run the container for ms locally and enter the ip of container in /etc/hosts corresponding to the k8s service name.In this the same code will work.
Any other better solutions are welcomed.
😔😔😭😭
Did you consider using spring boot profiles for this purpose? We are using it effectively for long across our teams. For this purpose, you'll have to extract the service(s) host as separate properties in application.yml (or application.properties) and use this host in rest of the properties as a variable. Following snippet explains this
application.yml
----------------
serviceA:
host: service-A-Name
api-one-endpoint: http://${serviceA.host}/api/v1/one
api-two-endpoint: http://${serviceA.host}/api/v1/two
api-three-endpoint: http://${serviceA.host}/api/v1/three
api-four-endpoint: http://${serviceA.host}/api/v1/four
In production (any hosted/managed environment for that matter), you provide appropriate value for spring property serviceA.host. In your use case, you'll be using this value AS-IS and provide k8s service name binding instead.
For local dev environment, you only need to override single property. For simple use case (say you need to override only single property), you can pass it as an agrument to your spring boot launcher (e.g. "--serviceA.host=localhost"). If you have many services (you likely do) even then you'll need to override well known few host name properties only. Using a dedicated dev profiles is much better in this case. Following example illustrate same scenario
application-dev.yml
-------------------
serviceA:
host: mylocalhost:9090
Then you use this profile in your eclipse/intellij launcher configuraiton for execution or debugging purpose by adding "--spring.profiles.active=dev" as and additional argument and spring boot will use updated host from dev profile. In fact combining these two approaches gives you even more flexibility for advance cases. If you agree on a common port convention across team then you can even check-in application-dev.yml for usage by everyone pretty much as-is.
spring boot profiles is much more powerful feature, I'll strongly recommend to go through it's documentation and few tutorial (like this one) to understand it fully and exploit it effectively for use cases like this one.

Spring Boot 2 how to change startup behaviour

do not judge this question) I want to implement WEB installer for my Spring Boot application, and very interesting moment is that my application plays 2 role: Installer and Backend(Application). When i first run my app i need to tell Spring to not initialize particular beans(Hibernate(while startup application must not to be failed to start because database may not exist), ActiveMq and others beans that will be added in installation process) and show some html pages with installation guide. Also i need to prevent access to endpoints where some logic with database occurs. When installation finished i will create new application.properties or some other file with settings and i tell Spring to initialize all required beans with Hibernate, ActiveMQ and others. Maybe i will make restart of application and new behaviour that based on installation will occur. And in next starts my application will not show installation guide. To simplify the question: I need to change startup behaviour of Spring Boot Application. For fun i can give an example with human: I need to make human live with no organs, and this human will live very good, and if i want i can add organs to human and he will be live very well))
You can use #Profile annotation. Check this link: https://www.mkyong.com/spring/spring-profiles-example/

Inspektr and its usage

I was going through details of CAS project and found that it is using something called inspektr. I googled for some time and tried to find more details about its usage. But I did not get any information.
Can anyone provide more details about it and its usage.
Thanks in advance.
Inspektr can be found here: https://github.com/dima767/inspektr with details for usage here: https://github.com/dima767/inspektr/wiki/Inspektr-Auditing
As I understand the project, it collects information from your web flow and allows you to save said data through the use of the #Audit annotations provided. If the configuration is copied from that CAS project you linked, nearly everything's configured to log to a file. Sample data logged would be the Client's IP, remote IP, the action being performed (as configured via Spring and the #Audit annotation), as well as various other things.
If you're familiar with Spring Aspects, it should be a breeze to look through the Inspektr source code to find other uses.
Inspektr is a framework that allows us to drive audit records from Annotations utilizing an Aspect that is provided with the framework. This works for Spring Managed Beans only!
Here the github project website:
https://github.com/dima767/inspektr/wiki/Inspektr-Auditing
A good practical reference for config: https://wiki.jasig.org/display/CASUM/Auditing+and+Statistics+Via+Inspektr
The base principal here is that Inspektr allows for logging of these audit frames into the console, database, the application server log ,we can even define our own managers to log to a different medium if required.

Categories