From 846f1c95a8bb89dff4ecd96d15bb79c22a23371a Mon Sep 17 00:00:00 2001 From: Nicolas Labrot Date: Fri, 8 Nov 2013 23:06:56 +0100 Subject: [PATCH] Allow async initialization of Node and Client #29 --- README.md | 19 ++++- pom.xml | 6 ++ ...lasticsearchAbstractClientFactoryBean.java | 38 +++++++++- .../ElasticsearchAbstractFactoryBean.java | 23 ++++++ .../ElasticsearchNodeFactoryBean.java | 72 ++++++++++++------ .../proxy/GenericInvocationHandler.java | 32 ++++++++ .../xml/ClientBeanDefinitionParser.java | 18 ++++- .../xml/NodeBeanDefinitionParser.java | 13 +++- .../elasticsearch/xml/elasticsearch-0.2.xsd | 21 ++++++ .../xml/ElasticsearchAsyncClientTest.java | 67 +++++++++++++++++ .../ElasticsearchAsyncNodeAndClient4Test.java | 74 +++++++++++++++++++ .../ElasticsearchAsyncNodeAndClientTest.java | 63 ++++++++++++++++ .../xml/ElasticsearchAsyncNodeTest.java | 68 +++++++++++++++++ .../elasticsearch/xml/es-async-client.xml | 33 +++++++++ .../xml/es-async-node-client.xml | 33 +++++++++ .../xml/es-async-node-client4.xml | 44 +++++++++++ .../elasticsearch/xml/es-async-node.xml | 33 +++++++++ 17 files changed, 628 insertions(+), 29 deletions(-) create mode 100644 src/main/java/fr/pilato/spring/elasticsearch/proxy/GenericInvocationHandler.java create mode 100644 src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncClientTest.java create mode 100644 src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClient4Test.java create mode 100644 src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClientTest.java create mode 100644 src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeTest.java create mode 100644 src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-client.xml create mode 100644 src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client.xml create mode 100644 src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client4.xml create mode 100644 src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node.xml diff --git a/README.md b/README.md index 92685ab9..a0c43baf 100644 --- a/README.md +++ b/README.md @@ -33,7 +33,7 @@ Import spring-elasticsearch in you project `pom.xml` file: fr.pilato.spring spring-elasticsearch - 0.2.0 + 0.2.0-SNAPSHOT ``` @@ -352,6 +352,18 @@ Just set `forceTemplate` property to `true`. ``` +### Asyncronous initialization + +Node and client beans initialization are by default synchronously. They can be initialized asynchronously with the attributes `async` and `taskExecutor`. + +```xml + + +``` +Aynchronous initialization does not block Spring startup but it continues on background on another thread. +Any methods call to these beans before elasticsearch is initialized will be blocker. `taskExecutor` references a standard Spring's task executor. + + Old fashion bean definition --------------------------- @@ -422,8 +434,11 @@ Note that you can use the old fashion method to define your beans instead of usi Thanks ------ -Special thanks to [Nicolas Huray](https://github.com/nhuray) for his contribution about +Special thanks to +- [Nicolas Huray](https://github.com/nhuray) for his contribution about [templates](https://github.com/dadoonet/spring-elasticsearch/pull/4) +- [Nicolas Labrot](https://github.com/nithril‎) for his contribution about +[async](https://github.com/dadoonet/spring-elasticsearch/pull/30) License diff --git a/pom.xml b/pom.xml index b2f9ef3b..adaca4e5 100644 --- a/pom.xml +++ b/pom.xml @@ -45,6 +45,12 @@ https://github.com/nhuray/ +1 + + nlabrot + Nicolas Labrot + https://github.com/nithril‎/ + Europe/Paris + diff --git a/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractClientFactoryBean.java b/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractClientFactoryBean.java index 07b3bd91..2e8ec792 100644 --- a/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractClientFactoryBean.java +++ b/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractClientFactoryBean.java @@ -19,6 +19,21 @@ package fr.pilato.spring.elasticsearch; +import fr.pilato.spring.elasticsearch.proxy.GenericInvocationHandler; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.lang.reflect.Proxy; +import java.util.ArrayList; +import java.util.Collection; +import java.util.HashMap; +import java.util.Iterator; +import java.util.Map; +import java.util.concurrent.Callable; +import java.util.concurrent.Future; + import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.elasticsearch.action.admin.indices.alias.IndicesAliasesResponse; @@ -162,6 +177,7 @@ public abstract class ElasticsearchAbstractClientFactoryBean extends Elasticsear protected final Log logger = LogFactory.getLog(getClass()); protected Client client; + protected Client proxyfiedClient; protected boolean forceMapping; @@ -324,6 +340,24 @@ public void setClasspathRoot(String classpathRoot) { public void afterPropertiesSet() throws Exception { logger.info("Starting ElasticSearch client"); + if (async) { + Assert.notNull(taskExecutor); + Future future = taskExecutor.submit(new Callable() { + @Override + public Client call() throws Exception { + return initialize(); + } + }); + proxyfiedClient = (Client) Proxy.newProxyInstance(Client.class.getClassLoader(), + new Class[]{Client.class}, new GenericInvocationHandler(future)); + + } else { + client = initialize(); + } + } + + + private Client initialize() throws Exception { client = buildClient(); if (autoscan) { computeMappings(); @@ -331,6 +365,8 @@ public void afterPropertiesSet() throws Exception { initTemplates(); initMappings(); initAliases(); + + return client; } @Override @@ -347,7 +383,7 @@ public void destroy() throws Exception { @Override public Client getObject() throws Exception { - return client; + return async ? proxyfiedClient : client; } @Override diff --git a/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractFactoryBean.java b/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractFactoryBean.java index 5eef1358..77bec2fb 100644 --- a/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractFactoryBean.java +++ b/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchAbstractFactoryBean.java @@ -22,6 +22,7 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.springframework.beans.factory.FactoryBean; +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; import java.util.Map; import java.util.Properties; @@ -40,6 +41,10 @@ public abstract class ElasticsearchAbstractFactoryBean { protected Properties properties; + protected boolean async = false; + + protected ThreadPoolTaskExecutor taskExecutor; + /** * Elasticsearch Settings file classpath URL (default : es.properties) *

Example :
@@ -94,5 +99,23 @@ public void setSettings(final Map settings) { */ public void setProperties(Properties properties) { this.properties = properties; + } + + /** + * Enable async initialization + * + * @param async + */ + public void setAsync(boolean async) { + this.async = async; + } + + /** + * Executor for async init mode + * + * @param taskExecutor + */ + public void setTaskExecutor(ThreadPoolTaskExecutor taskExecutor) { + this.taskExecutor = taskExecutor; } } diff --git a/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchNodeFactoryBean.java b/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchNodeFactoryBean.java index 825d1d58..85c7b950 100644 --- a/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchNodeFactoryBean.java +++ b/src/main/java/fr/pilato/spring/elasticsearch/ElasticsearchNodeFactoryBean.java @@ -19,6 +19,12 @@ package fr.pilato.spring.elasticsearch; +import fr.pilato.spring.elasticsearch.proxy.GenericInvocationHandler; + +import java.lang.reflect.Proxy; +import java.util.concurrent.Callable; +import java.util.concurrent.Future; + import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.elasticsearch.common.settings.ImmutableSettings; @@ -28,6 +34,8 @@ import org.springframework.beans.factory.DisposableBean; import org.springframework.beans.factory.FactoryBean; import org.springframework.beans.factory.InitializingBean; +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; +import org.springframework.util.Assert; /** * A {@link FactoryBean} implementation used to create a {@link Node} element @@ -46,34 +54,28 @@ public class ElasticsearchNodeFactoryBean extends ElasticsearchAbstractFactoryBe protected final Log logger = LogFactory.getLog(getClass()); private Node node; + private Node proxyfiedNode; @Override public void afterPropertiesSet() throws Exception { - final NodeBuilder nodeBuilder = NodeBuilder.nodeBuilder(); + if (async) { + Assert.notNull(taskExecutor); - if (null != settings && null == properties) { - logger.warn("settings has been deprecated in favor of properties. See issue #15: https://github.com/dadoonet/spring-elasticsearch/issues/15."); - nodeBuilder.getSettings().put(settings); - } + Future nodeFuture = taskExecutor.submit(new Callable() { + @Override + public Node call() throws Exception { + return initialize(); + } + }); + proxyfiedNode = (Node) Proxy.newProxyInstance(Node.class.getClassLoader(), + new Class[]{Node.class}, new GenericInvocationHandler(nodeFuture)); - if (null != settingsFile && null == properties) { - Settings settings = ImmutableSettings.settingsBuilder() - .loadFromClasspath(this.settingsFile) - .build(); - nodeBuilder.getSettings().put(settings); + } else { + node = initialize(); } - - if (null != properties) { - nodeBuilder.getSettings().put(properties); - } - - if (logger.isDebugEnabled()) logger.debug("Starting ElasticSearch node..."); - node = nodeBuilder.node(); - logger.info( "Node [" + node.settings().get("name") + "] for [" + node.settings().get("cluster.name") + "] cluster started..." ); - if (logger.isDebugEnabled()) logger.debug( " - data : " + node.settings().get("path.data") ); - if (logger.isDebugEnabled()) logger.debug( " - logs : " + node.settings().get("path.logs") ); } + @Override public void destroy() throws Exception { try { @@ -86,7 +88,7 @@ public void destroy() throws Exception { @Override public Node getObject() throws Exception { - return node; + return async ? proxyfiedNode : node; } @Override @@ -99,4 +101,32 @@ public boolean isSingleton() { return true; } + private Node initialize() { + final NodeBuilder nodeBuilder = NodeBuilder.nodeBuilder(); + + if (null != settings && null == properties) { + logger.warn("settings has been deprecated in favor of properties. See issue #15: https://github.com/dadoonet/spring-elasticsearch/issues/15."); + nodeBuilder.getSettings().put(settings); + } + + if (null != settingsFile && null == properties) { + Settings settings = ImmutableSettings.settingsBuilder() + .loadFromClasspath(this.settingsFile) + .build(); + nodeBuilder.getSettings().put(settings); + } + + if (null != properties) { + nodeBuilder.getSettings().put(properties); + } + + if (logger.isDebugEnabled()) logger.debug("Starting ElasticSearch node..."); + node = nodeBuilder.node(); + logger.info("Node [" + node.settings().get("name") + "] for [" + node.settings().get("cluster.name") + "] cluster started..."); + if (logger.isDebugEnabled()) logger.debug(" - data : " + node.settings().get("path.data")); + if (logger.isDebugEnabled()) logger.debug(" - logs : " + node.settings().get("path.logs")); + + return node; + } + } diff --git a/src/main/java/fr/pilato/spring/elasticsearch/proxy/GenericInvocationHandler.java b/src/main/java/fr/pilato/spring/elasticsearch/proxy/GenericInvocationHandler.java new file mode 100644 index 00000000..b83a842f --- /dev/null +++ b/src/main/java/fr/pilato/spring/elasticsearch/proxy/GenericInvocationHandler.java @@ -0,0 +1,32 @@ +package fr.pilato.spring.elasticsearch.proxy; + +import java.lang.reflect.InvocationHandler; +import java.lang.reflect.Method; +import java.util.concurrent.Future; + +import org.springframework.util.ReflectionUtils; + +/** + * @author labrot + * Date: 10/7/13 + * Time: 4:19 PM + */ +public class GenericInvocationHandler implements InvocationHandler { + + private volatile T bean; + private Future nodeFuture; + + public GenericInvocationHandler(Future nodeFuture) { + this.nodeFuture = nodeFuture; + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + if (bean == null) { + bean = nodeFuture.get(); + //release reference + nodeFuture = null; + } + return ReflectionUtils.invokeMethod(method, bean, args); + } +} diff --git a/src/main/java/fr/pilato/spring/elasticsearch/xml/ClientBeanDefinitionParser.java b/src/main/java/fr/pilato/spring/elasticsearch/xml/ClientBeanDefinitionParser.java index 3c7c7a98..7903bec4 100644 --- a/src/main/java/fr/pilato/spring/elasticsearch/xml/ClientBeanDefinitionParser.java +++ b/src/main/java/fr/pilato/spring/elasticsearch/xml/ClientBeanDefinitionParser.java @@ -58,6 +58,9 @@ public BeanDefinition parse(Element element, ParserContext parserContext) { String aliases = XMLParserUtil.getElementStringValue(element, "aliases"); String templates = XMLParserUtil.getElementStringValue(element, "templates"); + String taskExecutor = element.getAttribute("taskExecutor"); + String async = element.getAttribute("async"); + // Checking bean definition boolean isClientNode = (node != null && node.length() > 0); boolean isEsNodesEmpty = (esNodes == null || esNodes.length() == 0); @@ -77,13 +80,13 @@ public BeanDefinition parse(Element element, ParserContext parserContext) { bdef.setBeanClass(ElasticsearchClientFactoryBean.class); BeanDefinitionBuilder clientBuilder = startClientBuilder(ElasticsearchClientFactoryBean.class, settingsFile, properties, forceMapping, forceTemplate, mergeMapping, mergeSettings, autoscan, - classpathRoot, mappings, aliases, templates); + classpathRoot, mappings, aliases, templates, async, taskExecutor); client = ClientBeanDefinitionParser.buildClientDef(clientBuilder, node); } else { bdef.setBeanClass(ElasticsearchTransportClientFactoryBean.class); BeanDefinitionBuilder clientBuilder = startClientBuilder(ElasticsearchTransportClientFactoryBean.class, settingsFile, properties, forceMapping, forceTemplate, mergeMapping, mergeSettings, autoscan, - classpathRoot, mappings, aliases, templates); + classpathRoot, mappings, aliases, templates, async, taskExecutor); client = ClientBeanDefinitionParser.buildTransportClientDef(clientBuilder, esNodes); } @@ -119,7 +122,7 @@ public static BeanDefinitionBuilder startClientBuilder(Class beanClass, String s boolean forceMapping, boolean forceTemplate, boolean mergeMapping, boolean mergeSettings, boolean autoscan, String classpathRoot, String mappings, - String aliases, String templates) { + String aliases, String templates, String async, String taskExecutor) { BeanDefinitionBuilder nodeFactory = BeanDefinitionBuilder.rootBeanDefinition(beanClass); if (settingsFile != null && settingsFile.length() > 0) { logger.warn("settingsFile is deprecated. Use properties attribute instead. See issue #15: https://github.com/dadoonet/spring-elasticsearch/issues/15."); @@ -145,6 +148,15 @@ public static BeanDefinitionBuilder startClientBuilder(Class beanClass, String s if (templates != null && templates.length() > 0) { nodeFactory.addPropertyValue("templates", templates); } + + if (async != null && async.length() > 0) { + nodeFactory.addPropertyValue("async", async); + } + if (taskExecutor != null && taskExecutor.length() > 0) { + nodeFactory.addPropertyReference("taskExecutor", taskExecutor); + } + + return nodeFactory; } diff --git a/src/main/java/fr/pilato/spring/elasticsearch/xml/NodeBeanDefinitionParser.java b/src/main/java/fr/pilato/spring/elasticsearch/xml/NodeBeanDefinitionParser.java index 1ce246f1..5f07178a 100644 --- a/src/main/java/fr/pilato/spring/elasticsearch/xml/NodeBeanDefinitionParser.java +++ b/src/main/java/fr/pilato/spring/elasticsearch/xml/NodeBeanDefinitionParser.java @@ -41,9 +41,11 @@ public BeanDefinition parse(Element element, ParserContext parserContext) { String name = element.getAttribute("name"); String settingsFile = element.getAttribute("settingsFile"); String properties = element.getAttribute("properties"); + String taskExecutor = element.getAttribute("taskExecutor"); + String async = element.getAttribute("async"); // Define NodeBeanDefinition - BeanDefinition node = NodeBeanDefinitionParser.buildNodeDef(settingsFile, properties); + BeanDefinition node = NodeBeanDefinitionParser.buildNodeDef(settingsFile, properties, async, taskExecutor); // Register NodeBeanDefinition if (id != null && id.length() > 0) { @@ -55,7 +57,7 @@ public BeanDefinition parse(Element element, ParserContext parserContext) { return bdef; } - public static BeanDefinition buildNodeDef(String settingsFile, String properties) { + public static BeanDefinition buildNodeDef(String settingsFile, String properties, String async, String taskExecutor) { BeanDefinitionBuilder nodeFactory = BeanDefinitionBuilder.rootBeanDefinition(ElasticsearchNodeFactoryBean.class); if (settingsFile != null && settingsFile.length() > 0) { logger.warn("settingsFile is deprecated. Use properties attribute instead. See issue #15: https://github.com/dadoonet/spring-elasticsearch/issues/15."); @@ -64,6 +66,13 @@ public static BeanDefinition buildNodeDef(String settingsFile, String properties if (properties != null && properties.length() > 0) { nodeFactory.addPropertyReference("properties", properties); } + if (async != null && async.length() > 0) { + nodeFactory.addPropertyValue("async", async); + } + if (taskExecutor != null && taskExecutor.length() > 0) { + nodeFactory.addPropertyReference("taskExecutor", taskExecutor); + } + return nodeFactory.getBeanDefinition(); } diff --git a/src/main/resources/fr/pilato/spring/elasticsearch/xml/elasticsearch-0.2.xsd b/src/main/resources/fr/pilato/spring/elasticsearch/xml/elasticsearch-0.2.xsd index bc0638d5..d028b3be 100644 --- a/src/main/resources/fr/pilato/spring/elasticsearch/xml/elasticsearch-0.2.xsd +++ b/src/main/resources/fr/pilato/spring/elasticsearch/xml/elasticsearch-0.2.xsd @@ -58,6 +58,8 @@ ]]> + + @@ -201,7 +203,26 @@ ]]> + + + + + + + + + + + + + + + diff --git a/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncClientTest.java b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncClientTest.java new file mode 100644 index 00000000..469cf987 --- /dev/null +++ b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncClientTest.java @@ -0,0 +1,67 @@ +/* + * Licensed to David Pilato (the "Author") under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. Author licenses this + * file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package fr.pilato.spring.elasticsearch.xml; + +import java.lang.reflect.Proxy; +import java.util.concurrent.ExecutionException; + +import org.elasticsearch.client.Client; +import org.elasticsearch.node.Node; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.junit.Test; +import org.springframework.context.ConfigurableApplicationContext; +import org.springframework.context.support.ClassPathXmlApplicationContext; + +import static org.junit.Assert.assertNotNull; + + +public class ElasticsearchAsyncClientTest { + static protected ConfigurableApplicationContext ctx; + + @BeforeClass + static public void setup() { + ctx = new ClassPathXmlApplicationContext("fr/pilato/spring/elasticsearch/xml/es-async-client.xml"); + } + + @AfterClass + static public void tearDown() { + if (ctx != null) { + ctx.close(); + } + } + + @Test + public void test_node_client() throws Exception { + Node node = ctx.getBean(Node.class); + try { + Proxy.getInvocationHandler(node); + throw new Exception("Must not be proxyfied"); + } catch (IllegalArgumentException e) { + } + + Client client = ctx.getBean(Client.class); + Assert.assertNotNull(Proxy.getInvocationHandler(client)); + + assertNotNull("Client must not be null...", client); + client.admin().cluster().prepareState().execute().get(); + } +} diff --git a/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClient4Test.java b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClient4Test.java new file mode 100644 index 00000000..1e5f1061 --- /dev/null +++ b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClient4Test.java @@ -0,0 +1,74 @@ +/* + * Licensed to David Pilato (the "Author") under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. Author licenses this + * file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package fr.pilato.spring.elasticsearch.xml; + +import java.lang.reflect.Proxy; +import java.util.Map; +import java.util.concurrent.ExecutionException; + +import org.elasticsearch.client.Client; +import org.elasticsearch.node.Node; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.junit.Test; +import org.springframework.context.ConfigurableApplicationContext; +import org.springframework.context.support.ClassPathXmlApplicationContext; + +import static org.junit.Assert.assertNotNull; + + +public class ElasticsearchAsyncNodeAndClient4Test { + static protected ConfigurableApplicationContext ctx; + + @BeforeClass + static public void setup() { + ctx = new ClassPathXmlApplicationContext("fr/pilato/spring/elasticsearch/xml/es-async-node-client4.xml"); + } + + @AfterClass + static public void tearDown() { + if (ctx != null) { + ctx.close(); + } + } + + @Test + public void test_node_client() throws Exception { + Node node = ctx.getBean(Node.class); + Assert.assertNotNull(Proxy.getInvocationHandler(node)); + + Map clientMap = ctx.getBeansOfType(Client.class); + + for (Map.Entry entry : clientMap.entrySet()){ + if (entry.getKey().contains("async")){ + Assert.assertNotNull(Proxy.getInvocationHandler(entry.getValue())); + }else{ + try { + Proxy.getInvocationHandler(entry.getValue()); + throw new Exception("Must not be proxyfied"); + } catch (IllegalArgumentException e) { + } + } + } + //wait + node.isClosed(); + } +} diff --git a/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClientTest.java b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClientTest.java new file mode 100644 index 00000000..7c0f84d2 --- /dev/null +++ b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeAndClientTest.java @@ -0,0 +1,63 @@ +/* + * Licensed to David Pilato (the "Author") under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. Author licenses this + * file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package fr.pilato.spring.elasticsearch.xml; + +import java.lang.reflect.Proxy; +import java.util.concurrent.ExecutionException; + +import org.elasticsearch.client.Client; +import org.elasticsearch.node.Node; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.junit.Test; +import org.springframework.context.ConfigurableApplicationContext; +import org.springframework.context.support.ClassPathXmlApplicationContext; + +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertTrue; + + +public class ElasticsearchAsyncNodeAndClientTest { + static protected ConfigurableApplicationContext ctx; + + @BeforeClass + static public void setup() { + ctx = new ClassPathXmlApplicationContext("fr/pilato/spring/elasticsearch/xml/es-async-node-client.xml"); + } + + @AfterClass + static public void tearDown() { + if (ctx != null) { + ctx.close(); + } + } + + @Test + public void test_node_client() throws ExecutionException, InterruptedException { + Node node = ctx.getBean(Node.class); + Assert.assertNotNull(Proxy.getInvocationHandler(node)); + Client client = ctx.getBean("testNodeClient", Client.class); + Assert.assertNotNull(Proxy.getInvocationHandler(client)); + + assertNotNull("Client must not be null...", client); + client.admin().cluster().prepareState().execute().get(); + } +} diff --git a/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeTest.java b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeTest.java new file mode 100644 index 00000000..97694455 --- /dev/null +++ b/src/test/java/fr/pilato/spring/elasticsearch/xml/ElasticsearchAsyncNodeTest.java @@ -0,0 +1,68 @@ +/* + * Licensed to David Pilato (the "Author") under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. Author licenses this + * file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package fr.pilato.spring.elasticsearch.xml; + +import java.lang.reflect.Proxy; +import java.util.concurrent.ExecutionException; + +import org.elasticsearch.client.Client; +import org.elasticsearch.node.Node; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.junit.Test; +import org.springframework.context.ConfigurableApplicationContext; +import org.springframework.context.support.ClassPathXmlApplicationContext; + +import static org.junit.Assert.assertNotNull; + + +public class ElasticsearchAsyncNodeTest { + static protected ConfigurableApplicationContext ctx; + + @BeforeClass + static public void setup() { + ctx = new ClassPathXmlApplicationContext("fr/pilato/spring/elasticsearch/xml/es-async-node.xml"); + } + + @AfterClass + static public void tearDown() { + if (ctx != null) { + ctx.close(); + } + } + + @Test + public void test_node_client() throws Exception { + Node node = ctx.getBean(Node.class); + Assert.assertNotNull(Proxy.getInvocationHandler(node)); + + Client client = ctx.getBean(Client.class); + try { + Proxy.getInvocationHandler(client); + throw new Exception("Must not be proxyfied"); + } catch (IllegalArgumentException e) { + } + + + assertNotNull("Client must not be null...", client); + client.admin().cluster().prepareState().execute().get(); + } +} diff --git a/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-client.xml b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-client.xml new file mode 100644 index 00000000..f335b776 --- /dev/null +++ b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-client.xml @@ -0,0 +1,33 @@ + + + + + + + + + + + + + diff --git a/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client.xml b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client.xml new file mode 100644 index 00000000..51018c34 --- /dev/null +++ b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client.xml @@ -0,0 +1,33 @@ + + + + + + + + + + + + + diff --git a/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client4.xml b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client4.xml new file mode 100644 index 00000000..d349c330 --- /dev/null +++ b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node-client4.xml @@ -0,0 +1,44 @@ + + + + + + + + + + + + + + + diff --git a/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node.xml b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node.xml new file mode 100644 index 00000000..140520fa --- /dev/null +++ b/src/test/resources/fr/pilato/spring/elasticsearch/xml/es-async-node.xml @@ -0,0 +1,33 @@ + + + + + + + + + + + + +