How to enable neo4j webadmin when using spring-data-neo4j? - java

I am bootstrapping a new project from the Accessing Neo4j Data with REST example. The example uses an embedded database rather than a standalone neo4j server, but I would like to use the Neo4J webadmin interface for visualisation of my data. How do I enable the webadmin interface starting from this configuration?
(They got WrappingNeoServerBootstrapper working in use WrappingNeoServerBootstrapper with spring-data-neo4j but a lot of knowledge is omitted from the answer, e.g. it is not even mentioned where to place to the configuration. Being new to POMs, Spring Boot and Neo4j I therefore can't make use of that answer.)

The example you are using needs some tweaking to enable the Neo4j browser. I started from a different example, the Accessing Data with Neo4j example and it worked well.
You will need to do the following:
Change the version on your spring boot pom to 1.2.1.Release:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.2.1.RELEASE</version>
</parent>
Add dependencies for Neo4jServer:
<dependency>
<groupId>org.neo4j.app</groupId>
<artifactId>neo4j-server</artifactId>
<version>2.1.5</version>
</dependency>
<dependency>
<groupId>org.neo4j.app</groupId>
<artifactId>neo4j-server</artifactId>
<version>2.1.5</version>
<classifier>static-web</classifier>
</dependency>
Implement the Spring Boot command line runner in your Application.class:
public class Application extends Neo4jConfiguration implements CommandLineRunner{
Autowire a reference to your GraphDatabaseService in your Application.class:
#Autowired
GraphDatabaseService db;
#Override the run method from CommanLineRunner in your Application.class:
#Override
public void run(String... strings) throws Exception {
// used for Neo4j browser
try {
WrappingNeoServerBootstrapper neoServerBootstrapper;
GraphDatabaseAPI api = (GraphDatabaseAPI) db;
ServerConfigurator config = new ServerConfigurator(api);
config.configuration()
.addProperty(Configurator.WEBSERVER_ADDRESS_PROPERTY_KEY, "127.0.0.1");
config.configuration()
.addProperty(Configurator.WEBSERVER_PORT_PROPERTY_KEY, "8686");
neoServerBootstrapper = new WrappingNeoServerBootstrapper(api, config);
neoServerBootstrapper.start();
} catch(Exception e) {
//handle appropriately
}
// end of Neo4j browser config
}
When you are all done, your Application.class should look like this:
package hello;
import org.neo4j.graphdb.GraphDatabaseService;
import org.neo4j.graphdb.factory.GraphDatabaseFactory;
import org.neo4j.kernel.GraphDatabaseAPI;
import org.neo4j.server.WrappingNeoServerBootstrapper;
import org.neo4j.server.configuration.Configurator;
import org.neo4j.server.configuration.ServerConfigurator;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.data.neo4j.config.EnableNeo4jRepositories;
import org.springframework.data.neo4j.config.Neo4jConfiguration;
import org.springframework.data.rest.webmvc.config.RepositoryRestMvcConfiguration;
#Configuration
#EnableNeo4jRepositories
#Import(RepositoryRestMvcConfiguration.class)
#EnableAutoConfiguration
public class Application extends Neo4jConfiguration implements CommandLineRunner{
public Application() {
setBasePackage("hello");
}
#Bean(destroyMethod = "shutdown")
public GraphDatabaseService graphDatabaseService() {
return new GraphDatabaseFactory().newEmbeddedDatabase("target/hello.db");
}
#Autowired
GraphDatabaseService db;
#Override
public void run(String... strings) throws Exception {
// used for Neo4j browser
try {
WrappingNeoServerBootstrapper neoServerBootstrapper;
GraphDatabaseAPI api = (GraphDatabaseAPI) db;
ServerConfigurator config = new ServerConfigurator(api);
config.configuration()
.addProperty(Configurator.WEBSERVER_ADDRESS_PROPERTY_KEY, "127.0. 0.1");
config.configuration()
.addProperty(Configurator.WEBSERVER_PORT_PROPERTY_KEY, "8686");
neoServerBootstrapper = new WrappingNeoServerBootstrapper(api, config);
neoServerBootstrapper.start();
} catch(Exception e) {
//handle appropriately
}
// end of Neo4j browser config
}
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
The Neo4j browser will be available on the host and port configured in your run() method.

Related

Vaadin with Apache CXF SOAP service

I am new to Vaadin, just generated the application in Vaadin web site and built it locally. Then I added Apache CXF SOAP service to it, but I am unable to use the Tomcat that Vaadin is using, but instead I load SOAP in Jetty using:
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf-rt-transports-http-jetty</artifactId>
<version>${cxf.version}</version>
<scope>compile</scope>
</dependency>
My Vaadin application is:
#SpringBootApplication
#Theme(value = "iciclient", variant = Lumo.DARK)
#PWA(name = "ICI Client", shortName = "ICI Client", offlineResources = {"images/logo.png"})
public class Application extends SpringBootServletInitializer implements AppShellConfigurator {
public static void main(String[] args) {
LaunchUtil.launchBrowserInDevelopmentMode(SpringApplication.run(Application.class, args));
try {
System.out.println("Starting IciEventClient");
Object implementor = new IciEventServiceSoap12Impl();
String address = "http://localhost:8081/ici/IciEventService";
Endpoint.publish(address, implementor);
// http://localhost:8081/ici/IciEventService?WSDL
} catch (Exception e) {
e.printStackTrace();
}
}
}
While this works, I would like to get rid of separate Jetty dependency and run the SOAP service in Vaadin Tomcat (localhost:8080).
Should be simple but I can't figure out how to do it.
I think that it needs a separate servlet and route, but I don't know how to add them.
There is no web.xml in the Vaadin application, for example.
I am not familiar with Apache CXF, but based on CXF docs and the sample project I think I got it to work.
I downloaded a new Vaadin 14/Java 8 project from start.vaadin.com, and did the following:
Added the dependency
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf-spring-boot-starter-jaxws</artifactId>
<version>3.4.3</version>
</dependency>
Created a web service
import javax.jws.WebMethod;
import javax.jws.WebService;
#WebService
public class Test {
#WebMethod
public String test() {
return "This works";
}
}
Exposed it as a bean in my Application class
import javax.xml.ws.Endpoint;
import org.apache.cxf.Bus;
import org.apache.cxf.jaxws.EndpointImpl;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;
import org.springframework.context.annotation.Bean;
import org.vaadin.artur.helpers.LaunchUtil;
import org.vaadin.erik.endpoint.Test;
#SpringBootApplication
public class Application extends SpringBootServletInitializer {
public static void main(String[] args) {
LaunchUtil.launchBrowserInDevelopmentMode(SpringApplication.run(Application.class, args));
}
#Bean
public Endpoint test(Bus bus) {
EndpointImpl endpoint = new EndpointImpl(bus, new Test());
endpoint.publish("/Test");
return endpoint;
}
}
That was it! At least I can now list the service definition at http://localhost:8080/services/Test?wsdl
The first documentation link lists some configurations you can do, for example to change the /services path. The example project shows how to configure Spring actuator metrics if that is something you need.
You might want to create a separate #Configuration-annotated class for all your service #Bean definitions.
If you don't want to use the starter dependency, this Baeldung article looks promising.

Apache Camel Context start failure

I am pretty new to Spring Boot, Apache Camel and the ActiveMQ broker. I am trying to create an application which will send a message to a queue which I am hosting locally using Camel for routing.
POM:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-activemq</artifactId>
</dependency>
<dependency>
<groupId>org.apache.camel</groupId>
<artifactId>camel-core</artifactId>
<version>2.22.0</version>
</dependency>
<dependency>
<groupId>org.apache.camel</groupId>
<artifactId>camel-activemq</artifactId>
<version>3.2.0</version>
</dependency>
MsgRouteBuilder:
public void configure() throws Exception {
from("direct:firstRoute")
.setBody(constant("Hello"))
.to("activemq:queue:myQueue");
}
application.yaml:
activemq:
broker-url: tcp://localhost:61616
user: meAd
password: meAd
MainApp.java:
package me.ad.myCamel;
import org.apache.camel.CamelContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.EnableAspectJAutoProxy;
import me.ad.myCamel.router.MessageRouteBuilder;
#SpringBootApplication
#EnableAutoConfiguration(exclude={DataSourceAutoConfiguration.class})
#EnableAspectJAutoProxy(proxyTargetClass = true)
#EnableCaching
public class MeAdApp implements CommandLineRunner {
private static final Logger LOG = LoggerFactory.getLogger(MeAdApp.class);
public static void main(String[] args) {
try {
SpringApplication.run(MeAdApp.class, args);
} catch (Exception ex) {
LOG.error(ex.getMessage(), ex);
}
}
#Override
public void run(String... args) throws Exception {
LOG.info("Starting MeAdApp...");
}
}
MyController.java :
#GetMapping(value = "/routing")
public boolean sendToMyQueue() {
sendMyInfo.startRouting();
return true;
}
SendMyInfo.java :
MsgRouteBuilder routeBuilder = new MsgRouteBuilder();
CamelContext ctx = new DefaultCamelContext();
public void startRouting(){
try {
ctx.addRoutes(routeBuilder);
ctx.start();
Thread.sleep(5 * 60 * 1000);
ctx.stop();
}
catch (Exception e) {
e.printStackTrace();
}
}
So, whenever I call my rest end point: /routing, I get the error:
java.lang.NoSuchMethodError: org.apache.camel.RuntimeCamelException.wrapRuntimeException(Ljava/lang/Throwable;)Ljava/lang/RuntimeException;`
Can anybody please point me to the right direction as to why I am getting this error? Any help is greatly appreciated .
You need to have the components of the same version. If you are using camel-core with 3.2.0, use camel-activemq 3.2.0. And, since you are using spring-boot, you can make use of the starter dependencies. Just add these and you are good to go.
<dependency>
<groupId>org.apache.camel.springboot</groupId>
<artifactId>camel-spring-boot-starter</artifactId>
<version>3.2.0</version>
</dependency>
<dependency>
<groupId>org.apache.camel.springboot</groupId>
<artifactId>camel-activemq-starter</artifactId>
<version>3.2.0</version>
</dependency>

java.lang.NoClassDefFoundError: org/omg/CORBA/COMM_FAILURE on client while creating simple spring boor rmi app

I am creating spring boot applicating using RmiServiceExporter on server and RmiProxyFactoryBean on client.When i start server everything seems ok, i get
[main] o.s.remoting.rmi.RmiServiceExporter: Binding service 'ServerServiceIF' to RMI registry: RegistryImpl[UnicastServerRef [liveRef: [endpoint:[localhost:1099](local),objID:[0:0:0, 0]]]]
Then i start my client which is also spring boot app and my service interface on client is connecting to the adress on localhost.
rmi://localhost:1099/ServerServiceIF
But when i try to call method of this interface i get
Exception in thread "main" java.lang.NoClassDefFoundError: org/omg/CORBA/COMM_FAILURE
at org.springframework.remoting.rmi.RmiClientInterceptorUtils.isCorbaConnectFailure(RmiClientInterceptorUtils.java:187)
at org.springframework.remoting.rmi.RmiClientInterceptorUtils.isConnectFailure(RmiClientInterceptorUtils.java:174)
at org.springframework.remoting.rmi.RmiClientInterceptor.isConnectFailure(RmiClientInterceptor.java:283)
at org.springframework.remoting.rmi.RmiClientInterceptor.doInvoke(RmiClientInterceptor.java:349)
at org.springframework.remoting.rmi.RmiClientInterceptor.invoke(RmiClientInterceptor.java:260)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:179)
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:213)
at com.sun.proxy.$Proxy38.auth(Unknown Source)
at com.cw.client.ClientApplication.main(ClientApplication.java:29)
Caused by: java.lang.ClassNotFoundException: org.omg.CORBA.COMM_FAILURE
at java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:582)
at java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:185)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:496)
... 9 more
Here are my server and client:
ServerApplication.java
package com.cw.server;
import com.cw.appif.ServerServiceIF;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.remoting.rmi.RmiServiceExporter;
#SpringBootApplication
public class ServerApplication {
#Bean
ServerServiceIF serverServiceIF() {
return new ServerService();
}
#Bean
RmiServiceExporter exporter(ServerServiceIF implementation) {
// Expose a service via RMI. Remote object URL is:
// rmi://<HOST>:<PORT>/<SERVICE_NAME>
// 1099 is the default port
Class<ServerServiceIF> serviceInterface = ServerServiceIF.class;
RmiServiceExporter exporter = new RmiServiceExporter();
exporter.setServiceInterface(serviceInterface);
exporter.setService(implementation);
exporter.setServiceName(serviceInterface.getSimpleName());
exporter.setRegistryPort(1099);
return exporter;
}
public static void main(String[] args) {
SpringApplication.run(ServerApplication.class, args);
}
}
ClientApplication.java
package com.cw.client;
import com.cw.appif.ServerServiceIF;
import com.cw.exceptions.AuthException;
import com.cw.models.User;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.remoting.rmi.RmiProxyFactoryBean;
#SpringBootApplication
public class ClientApplication {
private static User user;
#Bean
RmiProxyFactoryBean service() {
RmiProxyFactoryBean rmiProxyFactory = new RmiProxyFactoryBean();
rmiProxyFactory.setServiceUrl("rmi://localhost:1099/ServerServiceIF");
rmiProxyFactory.setServiceInterface(ServerServiceIF.class);
return rmiProxyFactory;
}
public static void main(String[] args) {
try {
ServerServiceIF service = SpringApplication.run(ClientApplication.class, args).
getBean(ServerServiceIF.class);
user = new User("Denis","1234","e#mail.co");
service.auth(user);
System.out.println("User authed");
} catch (AuthException e) {
e.printStackTrace();
}
}
}
My server service interface and implementation on server:
package com.cw.appif;
import com.cw.exceptions.AuthException;
import com.cw.models.User;
public interface ServerServiceIF{
boolean auth(User user) throws AuthException;
}
package com.cw.server;
import com.cw.appif.ServerServiceIF;
import com.cw.exceptions.AuthException;
import com.cw.models.User;
import java.util.List;
public class ServerService implements ServerServiceIF{
static List<User> clients;
#Override
public boolean auth(User user) throws AuthException {
clients.add(user);
System.out.println("hi");
return true;
}
}
Heres my thoughts:
1)Maybe its because interface which im using is exactly the same on client and server, but client cant find class, because path is different?
2)When im debugging my client service->h->advised->targetSource ->targetClass is null. Is it ok? I will upload screenshots of my project structure and this variable in debug below.
server structure
client structure
debugging client
Found the problem. After adding corba to classpath, I found out that class User has to be Serializable. Adding implements Serializable and serialVersionUID fixed the problem and now everything is working.

Custom error pages in Spring Boot 1.4 not picked up when using JSP resolver

I am trying to use my own custom error pages in my Spring Boot 1.4 application. According to documentation, it should be sufficient to place my error pages in src/main/resources/public/error directory (for, example 404.html).
However, I am also using JSP pages in my application and have a resolver for them:
#Override
public void configureViewResolvers(final ViewResolverRegistry registry) {
final UrlBasedViewResolverRegistration resolver = registry.jsp("/WEB-INF/jsp/", ".jsp");
final Map<String, Object> attributes = new HashMap<>();
attributes.put("HASH", hashReader.getHashValue());
attributes.put("Hoker", hookerReader.getHooker());
resolver.attributes(attributes);
}
Whenever I experience an 4xx error, instead of using the custom error page I put in the resources/public/error directory, it tries to load /WEB-INF/jsp/error.jsp.
Is there a way how to force Spring Boot to use its default behavior instead of trying to resolve the error pages to the JSP directory?
here is an example, https://github.com/lenicliu/eg-spring/tree/master/eg-spring-boot/eg-spring-boot-webmvc
i guess u could fix it like this:
package com.lenicliu.spring.boot;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.context.embedded.ConfigurableEmbeddedServletContainer;
import org.springframework.boot.context.embedded.EmbeddedServletContainerCustomizer;
import org.springframework.boot.web.servlet.ErrorPage;
import org.springframework.context.annotation.Bean;
import org.springframework.http.HttpStatus;
#SpringBootApplication
public class Application {
#Bean
public EmbeddedServletContainerCustomizer customizeContainerr() {
return new CustomizedContainer();
}
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
private static class CustomizedContainer implements EmbeddedServletContainerCustomizer {
#Override
public void customize(ConfigurableEmbeddedServletContainer container) {
container.addErrorPages(new ErrorPage(HttpStatus.NOT_FOUND, "/404.html"));
container.addErrorPages(new ErrorPage(HttpStatus.INTERNAL_SERVER_ERROR, "/500.html"));
}
}
}
and u could put 404.html and 500.html into following folders:
src/main/resource/static/500.html
src/main/resource/static/404.html
OR like this:
container.addErrorPages(new ErrorPage(HttpStatus.NOT_FOUND, "/error/404.html"));
container.addErrorPages(new ErrorPage(HttpStatus.INTERNAL_SERVER_ERROR, "/error/500.html"));
and then put them into
src/main/resource/static/error/500.html
src/main/resource/static/error/404.html
reference to http://docs.spring.io/spring-boot/docs/1.4.2.RELEASE/reference/htmlsingle/#boot-features-spring-mvc-static-content
/static or /public or /resources or /META-INF/resources, them are same.
hope to help u :)

Run a Java class from Spring startup

I am using Java8 and Spring4.3.1.
I have a Java/Spring application hosting RESTfult services accessed by browser and mobile app clients. Second, I have written a Chat Server that listens for events (socket.io) from the clients. This Chat Server is running from the classes main method.
The Chat Server class has a main method that I want to run, and allow to listen for events when my Spring application starts. Is this possible?
If I run the main myself, it works, but I want it to start up when I start my Wildfly server that loads the Spring application.
Or is there a better approach? Should the Chat Server not be running from the main method?
I have the following code:
package com.jobs.spring.configuration;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRegistration.Dynamic;
import org.springframework.web.WebApplicationInitializer;
import org.springframework.web.context.support.AnnotationConfigWebApplicationContext;
import org.springframework.web.servlet.DispatcherServlet;
public class WebAppInitializer implements WebApplicationInitializer {
#Override
public void onStartup(ServletContext servletContext) throws ServletException {
AnnotationConfigWebApplicationContext ctx = new AnnotationConfigWebApplicationContext();
ctx.register(AppConfig.class);
ctx.setServletContext(servletContext);
Dynamic dynamic = servletContext.addServlet("rest", new DispatcherServlet(ctx));
dynamic.addMapping("/*");
dynamic.setLoadOnStartup(1);
try {
com.jobs.spring.chat.Server chatServer = new com.jobs.spring.chat.Server();
chatServer.run(null);
} catch (Exception e) {
e.printStackTrace();
}
}
}
and
public class Server implements CommandLineRunner {
private static final String SERVER = "localhost";
private static final Integer PORT = 3700;
#Override
public void run(String... args) throws Exception {
main(args);
}
public static void main(String[] args) {
...
and get the following error:
18:47:08,142 ERROR [org.jboss.msc.service.fail] (ServerService Thread Pool -- 66) MSC000001: Failed to start service jboss.undertow.deployment.default-server.default-host./jbosswildfly: org.jboss.msc.service.StartException in service jboss.undertow.deployment.default-server.default-host./jbosswildfly: java.lang.NoClassDefFoundError: Failed to link com/jobs/spring/chat/Server (Module "deployment.jbosswildfly.war:main" from Service Module Loader): org/springframework/boot/CommandLineRunner
Caused by: java.lang.NoClassDefFoundError: Failed to link com/jobs/spring/chat/Server (Module "deployment.jbosswildfly.war:main" from Service Module Loader): org/springframework/boot/CommandLineRunner
You could deploy your chat server in Wildfly, by extending SpringBootServletInitializer, instead of launching it from a main.
Documentation: howto-create-a-deployable-war-file
#SpringBootApplication
public class SpringBootApp extends SpringBootServletInitializer{
#Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {
return builder.sources(SpringBootApp.class);
}
//public static void main(String[] args){
// new SpringApplicationBuilder()
// .sources(SpringBootApp.class)
// .run(args);
//}
}
Change the artifact produced to war, and deploy it normally in wildfly:
<project>
<packaging>war</packaging>
...
<project>
You may have to exclude tomcat, which is automatically imported with spring-boot-starter-web:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
</exclusion>
</exclusions>
</dependency>
Spring provided a Spring Boot example of a pom.xml for wildfly: spring-boot-deployment-test-wildfly

Categories

Resources