support for rest-server-addon

This commit is contained in:
Michael Hunger
2011-03-23 22:20:19 +01:00
parent c25f9ddbbc
commit f7ddde14a0
7 changed files with 157 additions and 4 deletions

View File

@@ -16,7 +16,7 @@
<org.slf4j.version>1.5.10</org.slf4j.version>
<org.springframework.version>3.0.5.RELEASE</org.springframework.version>
<data.commons.version>1.0.0.BUILD-SNAPSHOT</data.commons.version>
<neo4j.version>1.3.M04</neo4j.version>
<neo4j.version>1.3-SNAPSHOT</neo4j.version>
<aspectj.version>1.6.11.M2</aspectj.version>
</properties>
<profiles>
@@ -229,6 +229,16 @@
<classifier>tests</classifier>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.neo4j</groupId>
<artifactId>server-api</artifactId>
<version>${neo4j.version}</version>
</dependency>
<dependency>
<groupId>commons-configuration</groupId>
<artifactId>commons-configuration</artifactId>
<version>1.6</version>
</dependency>
<dependency>
<groupId>org.ow2.jotm</groupId>

View File

@@ -132,6 +132,16 @@
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.neo4j</groupId>
<artifactId>server-api</artifactId>
</dependency>
<dependency>
<groupId>commons-configuration</groupId>
<artifactId>commons-configuration</artifactId>
</dependency>
<!-- JPA -->
<dependency>
<groupId>org.hibernate.javax.persistence</groupId>

View File

@@ -1,10 +1,14 @@
package org.springframework.data.graph.neo4j.config;
import org.neo4j.kernel.EmbeddedGraphDatabase;
import org.springframework.beans.factory.annotation.Autowire;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.beans.factory.support.BeanNameGenerator;
import org.springframework.beans.factory.xml.AbstractBeanDefinitionParser;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.context.annotation.ConfigurationClassPostProcessor;
import org.w3c.dom.Element;
import static org.springframework.util.StringUtils.hasText;
@@ -15,12 +19,29 @@ public class DataGraphBeanDefinitionParser extends AbstractBeanDefinitionParser
@Override
protected AbstractBeanDefinition parseInternal(Element element, ParserContext context) {
BeanDefinitionBuilder configBuilder = BeanDefinitionBuilder.rootBeanDefinition(Neo4jConfiguration.class);
BeanDefinitionBuilder configBuilder = createConfigurationBeanDefinition();
setupGraphDatabase(element, context, configBuilder);
setupEntityManagerFactory(element, configBuilder);
setupConfigurationClassPostProcessor(context);
return getSourcedBeanDefinition(configBuilder, element, context);
}
private BeanDefinitionBuilder createConfigurationBeanDefinition() {
BeanDefinitionBuilder configBuilder = BeanDefinitionBuilder.rootBeanDefinition(Neo4jConfiguration.class);
configBuilder.setAutowireMode(Autowire.BY_TYPE.value());
return configBuilder;
}
private void setupConfigurationClassPostProcessor(final ParserContext parserContext) {
BeanDefinitionRegistry beanDefinitionRegistry = parserContext.getRegistry();
BeanDefinitionBuilder configurationClassPostProcessor = BeanDefinitionBuilder.rootBeanDefinition(ConfigurationClassPostProcessor.class);
BeanNameGenerator beanNameGenerator = parserContext.getReaderContext().getReader().getBeanNameGenerator();
AbstractBeanDefinition configurationClassPostProcessorBeanDefinition = configurationClassPostProcessor.getBeanDefinition();
String beanName = beanNameGenerator.generateBeanName(configurationClassPostProcessorBeanDefinition, beanDefinitionRegistry);
beanDefinitionRegistry.registerBeanDefinition(beanName, configurationClassPostProcessorBeanDefinition);
}
@Override
protected boolean shouldGenerateId() {
return true;

View File

@@ -20,7 +20,7 @@ import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.neo4j.graphdb.PropertyContainer;
import org.neo4j.graphdb.index.Index;
import org.neo4j.index.impl.lucene.ValueContext;
import org.neo4j.index.lucene.ValueContext;
import org.springframework.data.annotation.Indexed;
import org.springframework.data.graph.annotation.NodeEntity;
import org.springframework.data.graph.core.GraphBacked;

View File

@@ -6,7 +6,6 @@ import org.neo4j.graphdb.PropertyContainer;
import org.neo4j.graphdb.index.Index;
import org.neo4j.graphdb.index.IndexHits;
import org.neo4j.helpers.collection.IterableWrapper;
import org.neo4j.index.impl.lucene.ValueContext;
import org.springframework.data.graph.core.GraphBacked;
import org.springframework.data.graph.neo4j.support.GraphDatabaseContext;

View File

@@ -0,0 +1,29 @@
package org.springframework.data.graph.neo4j.server;
import org.neo4j.graphdb.GraphDatabaseService;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.context.support.ClassPathXmlApplicationContext;
/**
* Context that merges the provided graph database service with the given context locations,
* so that spring beans that consume a graph database are populated properly.
*/
public class ProvidedClassPathXmlApplicationContext extends ClassPathXmlApplicationContext {
private final GraphDatabaseService database;
public ProvidedClassPathXmlApplicationContext(GraphDatabaseService database, final String[] locations)
throws org.springframework.beans.BeansException {
super();
setConfigLocations(locations);
this.database = database;
refresh();
}
@Override
protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
super.prepareBeanFactory(beanFactory);
beanFactory.registerResolvableDependency(GraphDatabaseService.class, database);
beanFactory.registerSingleton("graphDatabaseService", database);
}
}

View File

@@ -0,0 +1,84 @@
package org.springframework.data.graph.neo4j.server;
import org.apache.commons.configuration.Configuration;
import org.apache.commons.configuration.beanutils.BeanFactory;
import org.neo4j.graphdb.GraphDatabaseService;
import org.neo4j.server.plugins.PluginLifecycle;
import org.neo4j.server.plugins.Injectable;
import org.springframework.context.ApplicationContext;
import java.util.ArrayList;
import java.util.Collection;
/**
* Initializer to run Spring Data Graph based Server Plugins in a Neo4j REST-server. It takes the list of
* config locations and a number of spring beans from those contexts that should be exposed
* as injectable dependencies with a Jersey @Context.<br/>
* For example:</br>
* <pre>
* class MyInitializer extends SpringPluginInitializer {
* public MyInitializer() {
* super(new String[]{"myContext.xml"},"finderFactory","myRepository");
* }
* }
* </pre>
*/
public abstract class SpringPluginInitializer implements PluginLifecycle {
private String[] contextLocations;
private String[] exposedBeans;
protected ProvidedClassPathXmlApplicationContext ctx;
public SpringPluginInitializer(String[] contextLocations, String... exposedBeans) {
this.contextLocations = contextLocations;
this.exposedBeans = exposedBeans;
}
/**
* Binds the provided graph database to the spring contexts so that spring beans that consume a
* graph database can be populated.<br/>
* @param graphDatabaseService of the Neo4j server
* @param config of the Neo4j Server
* @return Exposes the requested Spring beans as @{see Injectable}s
*/
@Override
public Collection<Injectable<?>> start(GraphDatabaseService graphDatabaseService, Configuration config) {
ctx = new ProvidedClassPathXmlApplicationContext(graphDatabaseService, contextLocations);
Collection<Injectable<?>> result = new ArrayList<Injectable<?>>(exposedBeans.length);
for (final String exposedBean : exposedBeans) {
result.add(new SpringBeanInjectable(SpringPluginInitializer.this.ctx, exposedBean));
}
return result;
}
/**
* closes the spring context
*/
public void stop() {
if (ctx!=null) {
ctx.close();
}
}
/**
* provides access to the Spring bean, proxying the @{see Injectable}
* @param <T> optional type of the bean
*/
private static class SpringBeanInjectable<T extends Object> implements Injectable<T> {
private final String exposedBean;
protected ApplicationContext ctx;
public SpringBeanInjectable(final ApplicationContext ctx, String exposedBean) {
this.exposedBean = exposedBean;
this.ctx = ctx;
}
public T getValue() {
return (T) ctx.getBean(exposedBean);
}
public Class<T> getType() {
return (Class<T>) ctx.getType(exposedBean);
}
}
}