Code Monkey home page Code Monkey logo

solace-spring-boot's People

Contributors

carolmorneau avatar dependabot[bot] avatar matteofilia avatar mayur-solace avatar nephery avatar philippekhalife avatar tallisado avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

solace-spring-boot's Issues

[SOL-71913] Default Connect & Reconnect Settings

During the next major version we should consider whether or not to update the default connect and probably more importantly the reconnect settings. It seems like they were initially set to the current values b/c of the Developer guide says during a HA failover apps should retry to reconnect for "at least 5 minutes" - and we set the defaults to that minimum. But if reconnecting fails then in many cases your app is just done doing anything productive and we don't automatically stop your app. So unless you are checking the health and telling your app to restart then your app is just running and doing nothing. Because of this I wonder if we should default to a reconnect forever type scenario?

image

https://github.com/SolaceProducts/solace-spring-boot/blob/master/solace-spring-boot-autoconfigure/solace-java-spring-boot-autoconfigure/src/main/java/com/solace/spring/boot/autoconfigure/SolaceJavaProperties.java#L62

Solace client metrics in order to scale my application

I'm migrating from RabbitMQ to Solace, and there's a feature important in my spring boot applications with the rabbitmq client about metrics. We are using the metric rabbitmq.consumed to find the rate of consumed messages per second and scaling horizontally after a certain threshold.

I'm able to get this metric because the rabbit client delivers it for me as you can see here: https://blog.rabbitmq.com/posts/2016/11/metrics-support-in-rabbitmq-java-client-4-0/

That said, my question is: The solace client for java (sol-jcsmp) already delivers its metrics? If not, How I can have this metric?

simplify ssl client certificate auth configuration for Spring Boot Apps

Now a days we have to provide *.p12 files for authentication and five parameters explaining how to use the keystore:

    apiProperties:
      SSL_KEY_STORE: /somepath/file.jks
      SSL_KEY_STORE_FORMAT: JKS
      SSL_KEY_STORE_PASSWORD: password1
      SSL_PRIVATE_KEY_ALIAS: nameinkeystore
      SSL_PRIVATE_KEY_PASSWORD: password2   
      AUTHENTICATION_SCHEME: AUTHENTICATION_SCHEME_CLIENT_CERTIFICATE

this is not very handy when providing the spring boot / spring cloud stream application as docker container. Because best practice for kubernetes is it to provide secrets as environment variable.

Solace seams to mention this on its own:
Because with sol-jcsmp 10.14.0 there is a new option: SSL_IN_MEMORY_KEY_STORE

This option can not be used in a spring application.yaml file.

There for i propose 2 new options:

    apiProperties:
      SSL_KEY: <PEM Key>
      SSL_TRUST: <List of PEM certs>
  • The binder would read those variable.
  • create a KeyStore from the x509 string
  • provides the SSL_IN_MEMORY_KEY_STORE containing the generated KeyStore

Sample code: how to get from x509 to a KeyStore.

import static java.nio.charset.StandardCharsets.ISO_8859_1;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.security.KeyFactory;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.cert.Certificate;
import java.security.cert.CertificateException;
import java.security.cert.CertificateFactory;
import java.security.spec.InvalidKeySpecException;
import java.security.spec.PKCS8EncodedKeySpec;
import java.util.Arrays;
import java.util.Base64;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * Example code to create a Java keystore from a certificate and a private key.
 * <p>
 * The example certificate has been created with the following openssl command:
 * 
 * <pre>
 * openssl req -new -newkey rsa:2048 -x509 -days 365 -nodes -keyout privatekey.pem -out cert.pem
 * </pre>
 */

public class KeystoreBuilder {

	/**
	 * Retrieve this value from configuration.
	 */
	static final String CERTIFICATE = "-----BEGIN CERTIFICATE-----\n" //
			+ "MIICojCCAYoCCQCumQlzsNV9DDANBgkqhkiG9w0BAQsFADATMREwDwYDVQQDDAh0\n" //
			+ "ZXN0LmNvbTAeFw0yMjA3MDYwODUxNThaFw0yMzA3MDYwODUxNThaMBMxETAPBgNV\n" //
			+ "BAMMCHRlc3QuY29tMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAxozk\n" //
			+ "rkbXlye5SKyy6bfUMCFRNeycbATAjWjvLis3YVw38Hj7GbU64NYK/SI2eOFu5cAF\n" //
			+ "8ljLbMAyXSTbYA1p0jo2owhmA/hiM4bT9JNrsyMYRUhOnPVM9HWB0I8Yn4D8+i+J\n" //
			+ "WBaS0qh42SvCAxhZYn7I9mvpZxaPabfis4fFKXsuRGISYh4GIyTA2ZHgt/MLPBeL\n" //
			+ "hqdbmTexs7QtFik5Pl0cby5Mc0eFIbpqWwsfcN3QE74cCfPTronfgiZu7suwRKrw\n" //
			+ "lCRZ5OdR6/UogltHCEHi8x5HilxJj2NJJxW0BUUmTXHqLVTjR83lSBYQV8aG24T8\n" //
			+ "tEiYj/y0ZmSk1qwMNwIDAQABMA0GCSqGSIb3DQEBCwUAA4IBAQCS8TIfvMBui4uW\n" //
			+ "pYoAqvDDYVht+T2sP1zTrg6+V0CSULneTRm5YM9EFwSvyn1Uk7e2p7k0UXPi2moO\n" //
			+ "H9h/mr38xG4cJ8pPtzUvq6PmtMmRBMDV+i/nxqXjdzlR4vn03Qq1oD7ayW0t4CIi\n" //
			+ "N4SugpGFnsJ88JttjSNeaXWE0m11pyaT5p8WMv11XpU3riNMXiEI2yZHbP7mQUI5\n" //
			+ "x6wvQqKGLgBKkVuNiWPTJlLWQxtcaFyQqSusqQMuqmhZQFclZsTEmD+clFY08GAp\n" //
			+ "9fPsmNvi9dgLmKSNQ2Hb9F0Tuxw9mDmLJbA/ukgfQwOcElvvTtOxv0Vq5MumNFBS\n" //
			+ "UJFQEdAm\n" //
			+ "-----END CERTIFICATE-----";

	/**
	 * Retrieve this credential (!) from secure configuration.
	 */
	static final String PRIVATE_KEY = "-----BEGIN PRIVATE KEY-----\n" //
			+ "MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDGjOSuRteXJ7lI\n" //
			+ "rLLpt9QwIVE17JxsBMCNaO8uKzdhXDfwePsZtTrg1gr9IjZ44W7lwAXyWMtswDJd\n" //
			+ "JNtgDWnSOjajCGYD+GIzhtP0k2uzIxhFSE6c9Uz0dYHQjxifgPz6L4lYFpLSqHjZ\n" //
			+ "K8IDGFlifsj2a+lnFo9pt+Kzh8Upey5EYhJiHgYjJMDZkeC38ws8F4uGp1uZN7Gz\n" //
			+ "tC0WKTk+XRxvLkxzR4UhumpbCx9w3dATvhwJ89Ouid+CJm7uy7BEqvCUJFnk51Hr\n" //
			+ "9SiCW0cIQeLzHkeKXEmPY0knFbQFRSZNceotVONHzeVIFhBXxobbhPy0SJiP/LRm\n" //
			+ "ZKTWrAw3AgMBAAECggEAVsIoBtMjz4PnHY+BGkleaa2VS+fZLgYhkWkB4n211FA0\n" //
			+ "jVp/9mrPkIFXCedSQB3ZlIEE2DHeqeWN3E+HoIAb9mXDjBfWY/O8DWHj6iIk1IEI\n" //
			+ "UPXYjBNQDh3unJB6pO/7GuN8s0Yh3/UH4XWScEHKhRR7gdoDgi1Ee2CDqgkwqP/K\n" //
			+ "POU6p7vzB9iF1yFtZpcJhI2YcZuu8ZGjFn0bxdg5RW3BYRvlpRCGzAQNUkA4nkp5\n" //
			+ "LKhnm5UUxr4XJeOtcfYUAVhkogDqLVzBoxmvXxjYf5uw6Py8xxsXB58Q+gWf9Dik\n" //
			+ "5CkpARh2MnqzCer0sCK8/vWAECMHD4+t8LQkLGQ3mQKBgQDp54jBYxoyHdbaXGof\n" //
			+ "1OSJQ06kYtG+1z0VnIAqfVfUSC/wN3MvYp8YscCMKxx2QuqLU1esm1ws5/M+64UN\n" //
			+ "idGaCf8liBdoKp2cFSnEvXk2lIfLtXsLyZ9aMabe1f/q5GYygMqSBc3MIyEPs2t0\n" //
			+ "/5WslBa8n343ZIdH6twJjOt5PQKBgQDZTmYE2ZbAL5L8y8aRTUoiEpwklpJR5W/K\n" //
			+ "oy0EYqB3sWVVEDvabjVEMikufOfCwDMMMLXsPHr8/6Z6XQRYsxXe/QMK7xvKhov6\n" //
			+ "jJgJgAd6yH1J6aLuezwWyrdlGGT7Ex3bxZdOMYtw+gaZl12/p+aAdTJGbnYx1sAe\n" //
			+ "G07r0/0qgwKBgQCuiIvs8YvsdYOKcIbnta3KFqUp2Gr14hm8dIjWK61Lw4mxz05t\n" //
			+ "v0ND4+7vKIQWYpws1kWHkG3ZPEKvYoJntbznGip+0OvWWGY+vzPpkBBQf8hMYuCr\n" //
			+ "zQjQ/ler0zchCMiRSrTc/OOxPU1AL/sw1D3VBrNokAJYRvUC3ubNYY+baQKBgEYk\n" //
			+ "WiXCnjhWotlaZTPNgNpSq3fb6krpBhagaQ17UFSSPCUi4k71N9hVYJmS07Q3GcMb\n" //
			+ "jf084G39jxz8HUUMOUkK3gqPd6b9mv06mHColMF7KYXMFj1oJdMth9jn8OBiIUcp\n" //
			+ "Fle1Ak9rROoaw7XzWiGosputWBVqPgT5x5WzjYpFAoGBAOiKcQ5iw/dsDhsdbF2c\n" //
			+ "7Q+qJyAkGU4WmYN39c6rhJt7rb+vCuhAith6G8uMaD4BuRPMwWre093HAd31pSDR\n" //
			+ "1iDp1LNQ0G4MtohmgJgnc/+QXxZxJzvrcLr2QrASlA2DIgtxCek8ltpE6khJi533\n" //
			+ "dtKcxdEOiAAaGblmm6mk5YEr\n" //
			+ "-----END PRIVATE KEY-----";

	static Certificate[] getCertificates(String pem) throws CertificateException, IOException {
		var f = CertificateFactory.getInstance("X.509");
		try (var is = new ByteArrayInputStream(pem.getBytes(ISO_8859_1))) {
			return f.generateCertificates(is).toArray(new Certificate[0]);
		}
	}

	static PrivateKey getPrivateKey(String pem) throws NoSuchAlgorithmException, InvalidKeySpecException {
		var f = KeyFactory.getInstance("RSA");
		return f.generatePrivate(new PKCS8EncodedKeySpec(decodePEM(pem)));
	}

	private static Pattern PEM_FORMAT = Pattern.compile("(?m)(?s)^---*BEGIN.*---*$(.*)^---*END.*---*$.*");

	private static byte[] decodePEM(String pem) {
		Matcher matcher = PEM_FORMAT.matcher(pem);
		if (!matcher.matches()) {
			throw new IllegalArgumentException("Invalid PEM string");
		}
		return Base64.getMimeDecoder().decode(matcher.group(1));
	}

	static KeyStore createKeystore(PrivateKey key, Certificate[] certificates)
			throws KeyStoreException, NoSuchAlgorithmException, CertificateException, IOException {
		KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
		ks.load(null, null);
		ks.setKeyEntry("certificate", key, "changeit".toCharArray(), certificates);
		return ks;
	}

	public static void main(String[] args) throws Exception {
		var certs = getCertificates(CERTIFICATE);
		System.out.println(Arrays.toString(certs));

		var key = getPrivateKey(PRIVATE_KEY);
		System.out.println(key);

		KeyStore ks = createKeystore(key, certs);
		System.out.println(ks);
	}

}

Add `@ServiceConnection` support for Solace

Spring Boot 3.1 has introduced the notion of ConnectionDetails. You can read more about it this blog post. There's integration for both Testcontainers and Docker Compose where Spring Boot is able to source the details of the connection transparently.

Usually the connection details keep the "url" or "host" of the related server and authentication details. You can browse the Spring Boot code base to get an idea.

If you add support for this here, then @ServiceConnection would work transparently for Solace and we could even configure it automatically when an entry is created on start.spring.io. To get an idea, select Testcontainers and a supported entry (for instance Postgres). Let me know if I can help.

Add Github Action to automatically detect and test new Spring Boot version

We should add a Github action job (or update the existing one) to regularly check and test this project against new versions of Spring Boot.

What this probably has to do is just regularly poll Maven Central for any changes to Spring Boot. If a new one is detected, update the action's local repo (doesn't need to actually write to the repo), and run the tests.

If we need to make a new job for this, it would be nice if we could get a separate badge for it on the README if possible.

Health indicator

Spring comes with an integrated health indicator.
Here you can see the out of the box list:

https://github.com/joansmith2/spring-boot/blob/master/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/autoconfigure/HealthIndicatorAutoConfiguration.java#L30-L45

Those help for example in an kubernetes/OpenShift context to restart the pod if the broker connections was lost / the session was destroyed).To enshure that the pod is not running without jcsmp session and any possibility to recover this at some point.

Her is the it is a sample health check for JMS:
https://github.com/spring-projects/spring-boot/blob/master/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/jms/JmsHealthIndicator.java

Would you also provide an HelthIndicator for jcsmp?

Consider renaming auto-configurations

I was wondering if SolaceJava was a keyword of some sort? In the context of Spring Boot, the word "java" feels a bit odd. This is a breaking change though in case users are excluding the auto-configuration with the class name.

I suggest SolaceAutoConfiguration. I'd also replace SolaceJavaAutoCloudConfiguration so that the "cloud" keyword is not in the middle. CloudFoundrySolaceAutoConfiguration feels more natural to me.

How handle a different label for Solace

Hello,

I'm unsure if this is the right place to ask this question. If not, please let me know the right one.

At my company, we've been using the Cloundfoundry as PaaS, but the Solace service name is not solace-pubsub, so the library solace-java-cfenv does not work for me https://github.com/SolaceProducts/solace-spring-boot/tree/master/solace-java-cfenv.

I'm using this dependency in our Spring Boot applications, but it's not able to instantiate the SolaceJavaProperties and I need to do so on my side because of this issue.

<dependency>
	<groupId>com.solace.spring.boot</groupId>
	<artifactId>solace-java-spring-boot-starter</artifactId>
</dependency>

Best Regards

Project should use bom internally

The current structure is designed in such a way that the bom is a module like any other modules of this project. This defeats the purpose of testing dependency management internally and separating what is public and what isn't.

The content in its parent (solace-spring-boot-build)has a number of internal/project specific choices that the bom should not know about. The flatten maven plugin is used to publish a "cleaned" bom. That's a great idea but that doesn't shield you from something that may work here and fail in user's project.

A better arrangement would be to move everything build related from -build to -parent and make -parent inherit from the bom. The Spring Initializr project is a concrete example of such arrangement.

Consider Allowing JMS Autoconfig to use Java Credentials

Consider expanding the Spring Boot JMS autoconfig to use the solace.java credential properties if solace.jms ones are not specified. This would allow for an app that uses Spring Boot JMS in conjunction with the Spring Cloud Stream Binder or Spring Boot JCSMP to only have to specify credentials once rather than twice like shown below:

solace:
  java:
    host: ${host:tcp://localhost:55555}
    msgVpn: ${msgVpn:default}
    clientUsername: ${clientUsername:default}
    clientPassword: ${clientPassword:default}
  jms:
    host: ${host:tcp://localhost:55555}
    msgVpn: ${msgVpn:default}
    clientUsername: ${clientUsername:default}
    clientPassword: ${clientPassword:default}

Not able to connect to multiple VPNs within same host

Use case: I have this setup of Solace where message VPNs are separated based on the business domain. We are designing a Spring Boot application that needs to process the data for different domains using JMS.

Right now solace-spring-boot configuration allows only one message VPN to connect to while the brokers are generally set up with more than one VPNs based on the nature of messages.

Is there any plan to support multiple VPNs using the configuration?
Currently do we have any workaround to setup solace-spring-boot that can subscribe/publish to queues of different VPNs?

system-rules is not needed as a dependency

The following maven dependency is not needed:

		<groupId>com.github.stefanbirkner</groupId>
		<artifactId>system-rules</artifactId>
		<version>1.19.0</version>
		<scope>test</scope>

The only reason for including it is the transient dependency to junit 4.

I have made a pull request: #100

Spring Boot starters should not bring log4j

A typical Spring Boot starter (i.e. something that relies on spring-boot-starter), as the starters of this project, relies on the logging starter which brings the logging infrastructure that Spring Boot uses by default. The current default is logback and users can switch to another logging system as documented in the reference guide.

Currently, the starter brings log4j2. That's breaking the current arrangement. I assume that Solace and the rest of the infrastructure uses slf4j and therefore log4j2 is not a strict requirement. Please consider excluding log4j in the starter (or elsewhere) so that the default arrangement described above is respected.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.