Spring Data Couchbase Connecting via SSL - ssl

Is it possible to configure spring-data-couchbase to connect via SSL?
I have found documentation for how to do this via the SDK, but not in spring-data-couchbase 3.1.4-RELEASE

I think the way to do this is to extend AbstractCouchbaseConfiguration with your own configuration, and then Override the methods in that class with the SSL config as per the SDK documentation. For example:
#Configuration
public class CouchbaseConfig extends AbstractCouchbaseConfiguration {
#Override
public CouchbaseEnvironment couchbaseEnvironment() {
return DefaultCouchbaseEnvironment
.builder()
.sslEnabled(true)
.sslKeystoreFile("/path/tokeystore")
.sslKeystorePassword("password")
.build();
}
}

Related

Webflux access log header

How to customize the reactor access log in Spring webflux?
I am able to turn on reactor netty access log by setting
-Dreactor.netty.http.server.accessLogEnabled=true
I would like to customize the format, eg: I need a few request headers to be logged and remove the IP address.
Any hints to achieve this in Spring Webflux application would be helpful.
You can do it programmatically like this
#Component
public class MyNettyWebServerCustomizer
implements WebServerFactoryCustomizer<NettyReactiveWebServerFactory> {
#Override
public void customize(NettyReactiveWebServerFactory factory) {
factory.addServerCustomizers(httpServer -> httpServer.accessLog(true, x -> AccessLog.create("method={}, uri={}", x.method(), x.uri())));
}
}
More about custom access logging you can find in the documentation

Caching using #Cacheable with Spring MongoDB integration in spring boot and redis

I was wondering if it's possible to use #Cacheable annotations on the spring data mongo repositories. For example like this:
public interface UserRepository extends MongoRepository<User, String> {
#Cacheable("byId")
public interface UserRepository extends MongoRepository<User, String> {
User findById(String id);
}
}
I'd like to do it on the interface class itself and avoid having a wrapper class if possible. In addition, is there a sample for how to do the cache config for redis with java config (not xml)?
Yes, you can use Cacheable on any public method with spring aspects. You also have to use EnableCaching in any configuration class and optionally a CacheManager bean.

Bluemix force HTTPS on Spring Boot application

I have a Spring Boot application that is pushed on Bluemix as a CF app.
It works efficiently with the http protocol. However if i tried to force https, I get a 502 error.
I have:
#Configuration
class WebSecurityConfig extends WebSecurityConfigurerAdapter {
#Override
protected void configure(HttpSecurity http) throws Exception {
http.requiresChannel().anyRequest().requiresSecure();
//http.csrf().disable();
}
}
And I have an application.properties file with those entries:
server.ssl.key-store = classpath:**.jks
server.ssl.key-store-password = *******
server.ssl.key-password = ******
server.tomcat.remote_ip_header=x-forwarded-for
server.tomcat.protocol_header=x-forwarded-proto
I am aware that Bluemix performs SSL termination; in fact it sets correctly x-forwarded-proto and x-forwarded-for. I looked for solutions like 1 and 2 but without any luck.
I then tried with the following solution, as suggested in this article but a received a redirect loop insted:
#Bean
public TomcatEmbeddedServletContainerFactory tomcatEmbeddedServletContainerFactory(){
return new TomcatEmbeddedServletContainerFactory() {
#Override
protected void postProcessContext(Context context) {
SecurityConstraint securityConstraint = new SecurityConstraint();
securityConstraint.setUserConstraint("CONFIDENTIAL");
SecurityCollection collection = new SecurityCollection();
collection.addPattern("/*");
securityConstraint.addCollection(collection);
context.addConstraint(securityConstraint);
}
};
}
What did I miss in my approach? Many thanks for any tips/suggestions you may provide me
For the sake of the community, it would be good to see Rob's comment accepted as the answer. Rob, feel free to add your own answer if you would rather see that accepted instead.
Tomcat is not detecting the x-forwarded headers as being a trusted proxy. Try setting server.tomcat.internal-proxies=.* and logging.level.org.apache.catalina.valves=DEBUG

How can I configure a Swagger in Glassfish 4 without a web.xml?

The Swagger documentation covers a number of different ways to configure Swagger in an application. Unfortunately all of them leverage web.xml and rely on hard coding the api version and base url in the web.xml
Is there a way to configure Swagger without using a web.xml and without hardcoding the api version and base path?
I used the following approach to configure Swagger in Glassfish 4 without a resource XML.
Includes the following dependency in by gradle build file (this approach also applies to Maven):
compile ('com.wordnik:swagger-jaxrs_2.9.1:1.3.0') {
exclude group: 'org.scala-lang', module: 'scala-compiler'
}
Create a class that extends javax.ws.rs.core.Application and configure the ApplicationPath e.g.
#ApplicationPath("resources")
public class RESTConfig extends Application {}
2a. Create a class that extends com.wordnik.swagger.jaxrs.config.DefaultJaxrsConfig and annotate as follows:
#WebServlet(name = "SwaagerJaxrsConfig" initParams = {#WebInitParam(name="api.version", value="0.1.0"), #WebInitParam(name="swagger.api.basepath", value="http://localhost:8080/resources"})}, loadOnStartup = 2)
public class SwaagerJaxrsConfig extends DefaultJaxrsConfig{}
The downside of this approach is that the api version and base url of your app is hardcoded in the annotation. In order to get around this I used the following approach instead of the one above
2b. Create a class that extends HttpServlet and performs the bootstrapping done by DefaultJaxrsConfig e.g.
#WebServlet(name = "SwaggerJaxrsConfig", loadOnStartup = 2)
public class SwaggerJaxrsConfig extends HttpServlet {
private Logger log = Logger.getLogger(SwaggerJaxrsConfig.class);
#Inject Version version;
#Override public void init(ServletConfig servletConfig) {
try {
super.init(servletConfig);
SwaggerConfig swaggerConfig = new SwaggerConfig();
ConfigFactory.setConfig(swaggerConfig);
swaggerConfig.setBasePath("http://localhost:8080/resources"); //TODO look up app path
swaggerConfig.setApiVersion(version.getVersion());
ScannerFactory.setScanner(new DefaultJaxrsScanner());
ClassReaders.setReader(new DefaultJaxrsApiReader());
} catch (Exception e) {
log.error("Failed to configure swagger", e);
}
}
}

Dozer DozerBeanMapper Instantiation Startup EJB App Server Glassfish

Dozer's documentation states that you should only have one instance of DozerBeanMapper running in the app on the server. For initial development I ignored this, now I want to update the app to do this.
How can I instantiate the DozerBeanMapper class when the application starts on glassfish, and how would I access its "map" method in another class once the application has started or been newly deployed?
This is for EJBs so I can't use any servlet to do this.
OK, so I've finally had time to refactor this code. With the pointer from #Mikko Maunu, I am editing my question to provide the code that I have working for me for anyone who might find it useful in the future.
package com.xyz.utilities.singleton;
import javax.annotation.PostConstruct;
import javax.ejb.Singleton;
import javax.ejb.Startup;
import org.dozer.DozerBeanMapper;
#Startup
#Singleton
public class DozerInstantiator {
private DozerBeanMapper mapper = null;
#PostConstruct
void init() {
mapper = new DozerBeanMapper();
}
public DozerBeanMapper getMapper() {
return mapper;
}
}
And here is a straight forward usecase:
Inject an EJB member variable to your client class:
#EJB
DozerInstantiator di;
Within a method somewhere in the client class you can invoke the dozer mapper like so:
Credentials credentials = di.getMapper().map(credentialsDTO, Credentials.class);
// or
Credentials credentials = new Credentials();
di.getMapper().map(credentialsDTO, credentials);
If this is wrong or off base, someone please leave a comment. Until then, this seems to work so I'll use this solution I've developed with Mikko's input.
If you are using GlassFish 3.x, then you can use EJB 3.1 Singleton Session Bean:
#Startup //initialization in application startup
#Singleton //only one instance
public class DozerInitializer {
private String status;
#PostConstruct //executed once and only once when sole instance is created
void init {
//do steps needed to instantiate DozerBeanMapper
//here
}
}