DATACASS-290 - Support multiple Keyspaces using XML configuration.
We now support multiple Cassandra keyspaces by allowing multiple definitions of Sessions, Mapping Contexts, Converters and CassandraTemplates. Added support for id attribute for converter and mapping context elements and adopt CassandraMappingBeanFactoryPostProcessor to scan with eager initialization for existing infrastructure components. We are lenient about the source (factory bean or concrete bean definition) for infrastructure beans (Session, Converter, Mapping Context, Template) and register only the necessary beans. Original pull request: #76.
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-2014 the original author or authors
|
||||
* Copyright 2013-2016 the original author or authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -26,6 +26,15 @@ import org.springframework.beans.factory.support.BeanDefinitionBuilder;
|
||||
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
/**
|
||||
* Utilities to lookup {@link BeanDefinition bean definitions} for a {@link ListableBeanFactory} and to conditionally
|
||||
* register {@link BeanDefinition bean definitions}.
|
||||
*
|
||||
* @author Matthew Adams
|
||||
* @author Mark Paluch
|
||||
* @deprecated Will be removed with the next major release.
|
||||
*/
|
||||
@Deprecated
|
||||
public class BeanDefinitionUtils {
|
||||
|
||||
/**
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-2014 the original author or authors
|
||||
* Copyright 2013-2016 the original author or authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,34 +15,38 @@
|
||||
*/
|
||||
package org.springframework.data.cassandra.config;
|
||||
|
||||
import static org.springframework.data.cassandra.config.BeanDefinitionUtils.getBeanDefinitionsOfType;
|
||||
import static org.springframework.data.cassandra.config.BeanDefinitionUtils.*;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.beans.BeansException;
|
||||
import org.springframework.beans.factory.ListableBeanFactory;
|
||||
import org.springframework.beans.factory.config.BeanDefinition;
|
||||
import org.springframework.beans.factory.config.BeanDefinitionHolder;
|
||||
import org.springframework.beans.factory.config.BeanFactoryPostProcessor;
|
||||
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
|
||||
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
|
||||
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
|
||||
import org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor;
|
||||
import org.springframework.data.cassandra.convert.CassandraConverter;
|
||||
import org.springframework.data.cassandra.convert.MappingCassandraConverter;
|
||||
import org.springframework.data.cassandra.core.CassandraOperations;
|
||||
import org.springframework.data.cassandra.core.CassandraTemplate;
|
||||
import org.springframework.data.cassandra.mapping.CassandraMappingContext;
|
||||
import org.springframework.data.cassandra.mapping.BasicCassandraMappingContext;
|
||||
import org.springframework.data.cassandra.mapping.CassandraMappingContext;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
import com.datastax.driver.core.Session;
|
||||
|
||||
/**
|
||||
* {@link BeanDefinitionRegistryPostProcessor} that does its best to register any missing Spring Data Cassandra beans
|
||||
* that can be defaulted. Specifically, it attempts to create default bean definitions for the following required
|
||||
* interface types via their default implementation types:
|
||||
* {@link BeanFactoryPostProcessor} that does its best to register any missing Spring Data Cassandra beans that can be
|
||||
* defaulted. Specifically, it attempts to create default bean definitions for the following required interface types
|
||||
* via their default implementation types:
|
||||
* <ul>
|
||||
* <li>{@link CassandraOperations} via {@link CassandraTemplate}</li>
|
||||
* <li>{@link CassandraMappingContext} via {@link BasicCassandraMappingContext}</li>
|
||||
* <li> {@link CassandraConverter} via {@link MappingCassandraConverter}</li>
|
||||
* <li>{@link CassandraConverter} via {@link MappingCassandraConverter}</li>
|
||||
* </ul>
|
||||
* <p/>
|
||||
* If there are multiple definitions for any type that another type depends on, an {@link IllegalStateException} is
|
||||
@@ -57,59 +61,53 @@ import com.datastax.driver.core.Session;
|
||||
* It requires that a single {@link Session} or {@link CassandraSessionFactoryBean} definition be present. As described
|
||||
* above, multiple {@link Session} definitions, multiple {@link CassandraSessionFactoryBean} definitions, or both a
|
||||
* {@link Session} and {@link CassandraSessionFactoryBean} will cause an {@link IllegalStateException} to be thrown.
|
||||
*
|
||||
*
|
||||
* @author Matthew T. Adams
|
||||
* @author Mark Paluch
|
||||
* @deprecated Will be removed with the next major release. Spring Data Cassandra is not the best place to apply
|
||||
* configuration defaults.
|
||||
*/
|
||||
public class CassandraMappingBeanFactoryPostProcessor implements BeanDefinitionRegistryPostProcessor {
|
||||
|
||||
/**
|
||||
* Does nothing.
|
||||
*/
|
||||
@Override
|
||||
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {}
|
||||
@Deprecated
|
||||
public class CassandraMappingBeanFactoryPostProcessor implements BeanFactoryPostProcessor {
|
||||
|
||||
/**
|
||||
* Ensures that {@link BeanDefinition}s for a {@link CassandraMappingContext} and a {@link CassandraConverter} exist.
|
||||
*/
|
||||
@Override
|
||||
public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {
|
||||
public void postProcessBeanFactory(ConfigurableListableBeanFactory factory) throws BeansException {
|
||||
|
||||
if (!(registry instanceof ListableBeanFactory)) {
|
||||
if (!(factory instanceof BeanDefinitionRegistry)) {
|
||||
return;
|
||||
}
|
||||
ListableBeanFactory factory = (ListableBeanFactory) registry;
|
||||
|
||||
registerMissingDefaultableBeanDefinitions(registry, factory);
|
||||
registerMissingDefaultableBeanDefinitions((BeanDefinitionRegistry) factory, factory);
|
||||
}
|
||||
|
||||
protected void registerMissingDefaultableBeanDefinitions(BeanDefinitionRegistry registry, ListableBeanFactory factory) {
|
||||
private void registerMissingDefaultableBeanDefinitions(BeanDefinitionRegistry registry, ListableBeanFactory factory) {
|
||||
|
||||
// see if any template definitions exist, which requires a converter, which requires a mapping context
|
||||
BeanDefinitionHolder[] templateBeans = getBeanDefinitionsOfType(registry, factory, CassandraOperations.class, true,
|
||||
false);
|
||||
true);
|
||||
|
||||
if (templateBeans.length >= 1) {
|
||||
return;
|
||||
}
|
||||
|
||||
// need a session & converter for the default template
|
||||
|
||||
// see if an actual Session definition exists
|
||||
String sessionBeanName = findSessionBeanName(registry, factory);
|
||||
|
||||
// see if any converter bean definitions exist, which requires a mapping context
|
||||
BeanDefinitionHolder[] converterBeans = getBeanDefinitionsOfType(registry, factory,
|
||||
MappingCassandraConverter.class, true, false);
|
||||
BeanDefinitionHolder[] converterBeans = getBeanDefinitionsOfType(registry, factory, MappingCassandraConverter.class,
|
||||
true, false);
|
||||
|
||||
if (converterBeans.length > 1) {
|
||||
throw createAmbiguousBeansException(converterBeans.length, CassandraConverter.class, CassandraTemplate.class);
|
||||
}
|
||||
|
||||
if (converterBeans.length == 1) {
|
||||
|
||||
registerDefaultTemplate(registry, sessionBeanName, converterBeans[0].getBeanName());
|
||||
return;
|
||||
} else if (converterBeans.length > 1) {
|
||||
// then throw, because we need to create a default converter, but we wouldn't know which mapping context to use
|
||||
throw new IllegalStateException(String.format(
|
||||
"found %d beans of type [%s] - can't disambiguate for creation of [%s]", converterBeans.length,
|
||||
CassandraConverter.class.getName(), CassandraTemplate.class.getName()));
|
||||
}
|
||||
|
||||
// see if any mapping context bean definitions exist
|
||||
@@ -118,84 +116,85 @@ public class CassandraMappingBeanFactoryPostProcessor implements BeanDefinitionR
|
||||
|
||||
if (contextBeans.length > 1) {
|
||||
// then throw, because we need to create a default converter, but we wouldn't know which mapping context to use
|
||||
throw new IllegalStateException(String.format(
|
||||
"found %d beans of type [%s] - can't disambiguate for creation of [%s]", contextBeans.length,
|
||||
CassandraMappingContext.class.getName(), MappingCassandraConverter.class.getName()));
|
||||
throw createAmbiguousBeansException(contextBeans.length, MappingCassandraConverter.class,
|
||||
CassandraMappingContext.class);
|
||||
}
|
||||
|
||||
// create the mapping context if necessary
|
||||
BeanDefinitionHolder contextBean = contextBeans.length == 1 ? contextBeans[0] : null;
|
||||
if (contextBean == null) {
|
||||
contextBean = regsiterDefaultContext(registry);
|
||||
}
|
||||
BeanDefinitionHolder contextBean = contextBeans.length == 1 ? contextBeans[0] : registerDefaultContext(registry);
|
||||
|
||||
// create the default converter & template bean definitions
|
||||
BeanDefinitionHolder converter = registerDefaultConverter(registry, contextBean.getBeanName());
|
||||
registerDefaultTemplate(registry, sessionBeanName, converter.getBeanName());
|
||||
}
|
||||
|
||||
public String findSessionBeanName(BeanDefinitionRegistry registry, ListableBeanFactory factory) {
|
||||
private String findSessionBeanName(BeanDefinitionRegistry registry, ListableBeanFactory factory) {
|
||||
|
||||
// first, search for any session and session factory beans
|
||||
BeanDefinitionHolder[] sessionBeans = getBeanDefinitionsOfType(registry, factory, Session.class, true, false);
|
||||
BeanDefinitionHolder[] sessionFactoryBeans = getBeanDefinitionsOfType(registry, factory,
|
||||
CassandraSessionFactoryBean.class, true, false);
|
||||
BeanDefinitionHolder[] sessionBeans = getBeanDefinitionsOfType(registry, factory, Session.class, true, true);
|
||||
|
||||
int sessionCount = sessionBeans.length;
|
||||
int sessionFactoryCount = sessionFactoryBeans.length;
|
||||
int totalCount = sessionCount + sessionFactoryCount;
|
||||
|
||||
if (totalCount == 0 || totalCount > 1) { // can't create default template -- none or multiple
|
||||
throw createSessionException(totalCount, Session.class, CassandraSessionFactoryBean.class);
|
||||
}
|
||||
|
||||
if (sessionCount == 1) {
|
||||
if (sessionBeans.length == 1) { // can't create default template -- none or multiple
|
||||
return sessionBeans[0].getBeanName();
|
||||
}
|
||||
// else it must be the one session factory bean
|
||||
return sessionFactoryBeans[0].getBeanName();
|
||||
|
||||
throw createAmbiguousBeansException(sessionBeans.length, CassandraTemplate.class, Session.class,
|
||||
CassandraSessionFactoryBean.class);
|
||||
}
|
||||
|
||||
protected IllegalStateException createSessionException(int beanDefinitionCount, Class<?>... types) {
|
||||
private IllegalStateException createAmbiguousBeansException(int beanDefinitionCount, Class<?> defaultBeanType,
|
||||
Class<?>... types) {
|
||||
|
||||
return new IllegalStateException(String.format("found %d beans of type%s [%s] - %s for creation of default [%s]",
|
||||
beanDefinitionCount, beanDefinitionCount == 1 ? "" : "s", StringUtils.arrayToCommaDelimitedString(types),
|
||||
beanDefinitionCount == 0 ? "need exactly one" : "can't disambiguate", CassandraTemplate.class.getName()));
|
||||
return new IllegalStateException(
|
||||
String.format("found %d beans of type%s [%s] - %s for creation of default [%s]", beanDefinitionCount,
|
||||
beanDefinitionCount == 1 ? "" : "s", StringUtils.collectionToCommaDelimitedString(getNames(types)),
|
||||
beanDefinitionCount == 0 ? "need exactly one" : "can't disambiguate", defaultBeanType.getName()));
|
||||
}
|
||||
|
||||
protected BeanDefinitionHolder regsiterDefaultContext(BeanDefinitionRegistry registry) {
|
||||
private BeanDefinitionHolder registerDefaultContext(BeanDefinitionRegistry registry) {
|
||||
|
||||
BeanDefinitionHolder contextBean = new BeanDefinitionHolder(BeanDefinitionBuilder.genericBeanDefinition(
|
||||
BasicCassandraMappingContext.class).getBeanDefinition(), DefaultBeanNames.CONTEXT);
|
||||
BeanDefinitionHolder contextBean = new BeanDefinitionHolder(
|
||||
BeanDefinitionBuilder.genericBeanDefinition(BasicCassandraMappingContext.class).getBeanDefinition(),
|
||||
DefaultBeanNames.CONTEXT);
|
||||
|
||||
registry.registerBeanDefinition(contextBean.getBeanName(), contextBean.getBeanDefinition());
|
||||
|
||||
return contextBean;
|
||||
}
|
||||
|
||||
public BeanDefinitionHolder registerDefaultConverter(BeanDefinitionRegistry registry, String contextBeanName) {
|
||||
private BeanDefinitionHolder registerDefaultConverter(BeanDefinitionRegistry registry, String contextBeanName) {
|
||||
|
||||
BeanDefinitionBuilder converterBeanDefinitionBuilder = BeanDefinitionBuilder.genericBeanDefinition(
|
||||
MappingCassandraConverter.class).addConstructorArgReference(contextBeanName);
|
||||
BeanDefinitionHolder beanDefinition = new BeanDefinitionHolder(converterBeanDefinitionBuilder.getBeanDefinition(),
|
||||
DefaultBeanNames.CONVERTER);
|
||||
BeanDefinition beanDefinition = BeanDefinitionBuilder //
|
||||
.genericBeanDefinition(MappingCassandraConverter.class) //
|
||||
.addConstructorArgReference(contextBeanName).getBeanDefinition();
|
||||
|
||||
registry.registerBeanDefinition(beanDefinition.getBeanName(), beanDefinition.getBeanDefinition());
|
||||
BeanDefinitionHolder converter = new BeanDefinitionHolder(beanDefinition, DefaultBeanNames.CONVERTER);
|
||||
registry.registerBeanDefinition(converter.getBeanName(), converter.getBeanDefinition());
|
||||
|
||||
return beanDefinition;
|
||||
return converter;
|
||||
}
|
||||
|
||||
public BeanDefinitionHolder registerDefaultTemplate(BeanDefinitionRegistry registry, String sessionBeanName,
|
||||
private BeanDefinitionHolder registerDefaultTemplate(BeanDefinitionRegistry registry, String sessionBeanName,
|
||||
String converterBeanName) {
|
||||
|
||||
BeanDefinitionBuilder templateBeanDefinitionBuilder = BeanDefinitionBuilder
|
||||
.genericBeanDefinition(CassandraTemplate.class).addConstructorArgReference(sessionBeanName)
|
||||
.addConstructorArgReference(converterBeanName);
|
||||
BeanDefinition beanDefinition = templateBeanDefinitionBuilder.getBeanDefinition();
|
||||
BeanDefinition beanDefinition = BeanDefinitionBuilder.genericBeanDefinition(CassandraTemplate.class) //
|
||||
.addConstructorArgReference(sessionBeanName) //
|
||||
.addConstructorArgReference(converterBeanName) //
|
||||
.getBeanDefinition();
|
||||
|
||||
BeanDefinitionHolder template = new BeanDefinitionHolder(beanDefinition, DefaultBeanNames.TEMPLATE);
|
||||
registry.registerBeanDefinition(template.getBeanName(), template.getBeanDefinition());
|
||||
|
||||
return template;
|
||||
}
|
||||
|
||||
private Collection<String> getNames(Class<?>[] types) {
|
||||
|
||||
List<String> names = new ArrayList<String>();
|
||||
|
||||
for (Class<?> type : types) {
|
||||
names.add(type.getName());
|
||||
}
|
||||
|
||||
return names;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -775,6 +775,13 @@ Defines a CassandraMappingContext for holding rich entity mapping information.
|
||||
<xsd:element name="entity" type="entityType" minOccurs="0" maxOccurs="unbounded" />
|
||||
<xsd:element name="user-type-resolver" type="userTypeResolverType" minOccurs="0" maxOccurs="1" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="id" type="xsd:ID" use="optional">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation><![CDATA[
|
||||
The name of the mapping context; default is "cassandraMapping".
|
||||
]]></xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:attribute>
|
||||
<xsd:attribute name="entity-base-packages" type="xsd:string" use="optional">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation><![CDATA[
|
||||
|
||||
@@ -0,0 +1,171 @@
|
||||
/*
|
||||
* Copyright 2016 the original author or authors.
|
||||
*
|
||||
* Licensed 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 org.springframework.data.cassandra.config;
|
||||
|
||||
import static org.hamcrest.Matchers.*;
|
||||
import static org.junit.Assert.*;
|
||||
import static org.mockito.Mockito.*;
|
||||
|
||||
import org.junit.Rule;
|
||||
import org.junit.Test;
|
||||
import org.junit.rules.ExpectedException;
|
||||
import org.springframework.beans.factory.BeanCreationException;
|
||||
import org.springframework.beans.factory.config.AbstractFactoryBean;
|
||||
import org.springframework.context.support.GenericXmlApplicationContext;
|
||||
import org.springframework.data.cassandra.convert.CassandraConverter;
|
||||
import org.springframework.data.cassandra.core.CassandraOperations;
|
||||
import org.springframework.data.cassandra.mapping.CassandraMappingContext;
|
||||
|
||||
import com.datastax.driver.core.Session;
|
||||
|
||||
/**
|
||||
* Unit tests for {@link CassandraMappingBeanFactoryPostProcessor}.
|
||||
*
|
||||
* @author Mark Paluch
|
||||
*/
|
||||
public class CassandraMappingBeanFactoryPostProcessorTests {
|
||||
|
||||
@Rule public final ExpectedException expectedException = ExpectedException.none();
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void clusterRegistrationTriggersDefaultBeanRegistration() {
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "cluster-and-mock-session.xml");
|
||||
context.refresh();
|
||||
|
||||
assertThat(context.getBeanNamesForType(CassandraOperations.class), hasItemInArray("cqlTemplate"));
|
||||
assertThat(context.getBeanNamesForType(CassandraMappingContext.class), hasItemInArray("cassandraMapping"));
|
||||
assertThat(context.getBeanNamesForType(CassandraConverter.class), hasItemInArray("cassandraConverter"));
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void MappingAndConverterRegistrationTriggersDefaultBeanRegistration() {
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "mock-session-mapping-converter.xml");
|
||||
context.refresh();
|
||||
|
||||
assertThat(context.getBeanNamesForType(CassandraOperations.class), hasItemInArray("cqlTemplate"));
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void converterRegistrationFailsDueToMissingCassandraMapping() {
|
||||
|
||||
expectedException.expect(BeanCreationException.class);
|
||||
expectedException.expectMessage(containsString("No bean named 'cassandraMapping'"));
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "mock-session-converter.xml");
|
||||
context.refresh();
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void defaultBeanRegistrationShouldFailWithMultipleSessions() {
|
||||
|
||||
expectedException.expect(IllegalStateException.class);
|
||||
expectedException.expectMessage(allOf(containsString("found 2 beans of type"), containsString("Session")));
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "multiple-sessions.xml");
|
||||
context.refresh();
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void defaultBeanRegistrationShouldFailWithMultipleSessionFactories() {
|
||||
|
||||
expectedException.expect(IllegalStateException.class);
|
||||
expectedException.expectMessage(allOf(containsString("found 2 beans of type"), containsString("Session")));
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "multiple-session-factories.xml");
|
||||
context.refresh();
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void defaultBeanRegistrationShouldFailWithMultipleMappingContexts() {
|
||||
|
||||
expectedException.expect(IllegalStateException.class);
|
||||
expectedException
|
||||
.expectMessage(allOf(containsString("found 2 beans of type"), containsString("CassandraMappingContext")));
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "multiple-mapping-contexts.xml");
|
||||
context.refresh();
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void defaultBeanRegistrationShouldFailWithMultipleConvertersContexts() {
|
||||
|
||||
expectedException.expect(IllegalStateException.class);
|
||||
expectedException
|
||||
.expectMessage(allOf(containsString("found 2 beans of type"), containsString("CassandraConverter")));
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "multiple-converters.xml");
|
||||
context.refresh();
|
||||
}
|
||||
|
||||
/**
|
||||
* @see DATACASS-290
|
||||
*/
|
||||
@Test
|
||||
public void shouldAllowTwoKeyspaces() {
|
||||
|
||||
GenericXmlApplicationContext context = new GenericXmlApplicationContext();
|
||||
context.load(CassandraMappingBeanFactoryPostProcessorTests.class, "two-keyspaces-namespace.xml");
|
||||
context.refresh();
|
||||
|
||||
assertThat(context.getBeanNamesForType(CassandraOperations.class), arrayContaining("c-1", "c-2"));
|
||||
assertThat(context.getBeanNamesForType(CassandraMappingContext.class), arrayContaining("mapping-1", "mapping-2"));
|
||||
assertThat(context.getBeanNamesForType(CassandraConverter.class), arrayContaining("converter-1", "converter-2"));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private static class MockSessionFactory extends AbstractFactoryBean<Session> {
|
||||
|
||||
@Override
|
||||
public Class<?> getObjectType() {
|
||||
return Session.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Session createInstance() {
|
||||
return mock(Session.class);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<cass:cluster/>
|
||||
<bean class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,12 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<bean class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
<cass:converter />
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<bean class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
<cass:mapping/>
|
||||
<cass:converter/>
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,20 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<cass:cluster/>
|
||||
|
||||
<bean class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
|
||||
<cass:mapping/>
|
||||
<cass:converter/>
|
||||
|
||||
<bean class="org.springframework.data.cassandra.convert.MappingCassandraConverter">
|
||||
<constructor-arg index="0" ref="cassandraMapping"/>
|
||||
</bean>
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<cass:cluster/>
|
||||
<bean class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
<cass:mapping/>
|
||||
<bean class="org.springframework.data.cassandra.mapping.BasicCassandraMappingContext"/>
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<cass:cluster/>
|
||||
<cass:session id="session-1" keyspace-name="system"/>
|
||||
<cass:session id="session-2" keyspace-name="system"/>
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<cass:cluster/>
|
||||
<bean id="mockSession1" class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
<bean id="mockSession2" class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
|
||||
</beans>
|
||||
@@ -0,0 +1,24 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:cass="http://www.springframework.org/schema/data/cassandra"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/data/cassandra http://www.springframework.org/schema/data/cassandra/spring-cassandra-1.0.xsd
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
|
||||
|
||||
<cass:cluster/>
|
||||
|
||||
<bean id="keyspace-1"
|
||||
class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
<bean id="keyspace-2"
|
||||
class="org.springframework.data.cassandra.config.CassandraMappingBeanFactoryPostProcessorTests.MockSessionFactory"/>
|
||||
|
||||
<cass:mapping id="mapping-1"/>
|
||||
<cass:mapping id="mapping-2"/>
|
||||
|
||||
<cass:converter id="converter-1" mapping-ref="mapping-1"/>
|
||||
<cass:converter id="converter-2" mapping-ref="mapping-2"/>
|
||||
|
||||
<cass:template id="c-1" cassandra-converter-ref="converter-1" session-ref="keyspace-1"/>
|
||||
<cass:template id="c-2" cassandra-converter-ref="converter-2" session-ref="keyspace-2"/>
|
||||
|
||||
</beans>
|
||||
Reference in New Issue
Block a user