You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@geode.apache.org by es...@apache.org on 2017/11/03 00:51:31 UTC
[geode] branch feature/GEODE-3781 updated: implemented
regionToTable configuration property.
This is an automated email from the ASF dual-hosted git repository.
eshu11 pushed a commit to branch feature/GEODE-3781
in repository https://gitbox.apache.org/repos/asf/geode.git
The following commit(s) were added to refs/heads/feature/GEODE-3781 by this push:
new a97c762 implemented regionToTable configuration property.
a97c762 is described below
commit a97c762f93c3ad49ea70bb53bfa7c7c9aa2433c4
Author: eshu <es...@pivotal.io>
AuthorDate: Thu Nov 2 17:51:01 2017 -0700
implemented regionToTable configuration property.
---
.../jdbc/internal/JDBCConfiguration.java | 44 +++++++++++++++---
.../connectors/jdbc/internal/JDBCManager.java | 3 +-
.../jdbc/internal/JDBCConfigurationUnitTest.java | 45 ++++++++++++++++++-
.../jdbc/internal/JDBCManagerUnitTest.java | 52 ++++++++++++++++++----
4 files changed, 127 insertions(+), 17 deletions(-)
diff --git a/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCConfiguration.java b/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCConfiguration.java
index 058a6c9..142b9e3 100644
--- a/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCConfiguration.java
+++ b/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCConfiguration.java
@@ -24,6 +24,7 @@ import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.function.Function;
+import java.util.function.IntPredicate;
public class JDBCConfiguration {
private static final String URL = "url";
@@ -48,8 +49,14 @@ public class JDBCConfiguration {
*/
private static final String VALUE_CLASS_NAME = "valueClassName";
- private static final List<String> knownProperties = Collections
- .unmodifiableList(Arrays.asList(URL, USER, PASSWORD, VALUE_CLASS_NAME, IS_KEY_PART_OF_VALUE));
+ /**
+ * syntax: comma separated list of regionTableSpecs. regionTableSpecs: regionName followed by
+ * jdbcRegionSeparator followed by tableName. Whitespace is only allowed around the commas.
+ */
+ private static final String REGION_TO_TABLE = "regionToTable";
+
+ private static final List<String> knownProperties = Collections.unmodifiableList(
+ Arrays.asList(URL, USER, PASSWORD, VALUE_CLASS_NAME, IS_KEY_PART_OF_VALUE, REGION_TO_TABLE));
private static final List<String> requiredProperties =
Collections.unmodifiableList(Arrays.asList(URL));
@@ -61,6 +68,7 @@ public class JDBCConfiguration {
private final Map<String, String> regionToClassMap;
private final boolean keyPartOfValueDefault;
private final Map<String, Boolean> keyPartOfValueMap;
+ private final Map<String, String> regionToTableMap;
public JDBCConfiguration(Properties configProps) {
validateKnownProperties(configProps);
@@ -74,6 +82,11 @@ public class JDBCConfiguration {
String keyPartOfValueProp = configProps.getProperty(IS_KEY_PART_OF_VALUE);
this.keyPartOfValueDefault = computeDefaultKeyPartOfValue(keyPartOfValueProp);
this.keyPartOfValueMap = computeKeyPartOfValueMap(keyPartOfValueProp);
+ this.regionToTableMap = computeRegionToTableMap(configProps.getProperty(REGION_TO_TABLE));
+ }
+
+ private Map<String, String> computeRegionToTableMap(String prop) {
+ return parseMap(prop, v -> v, true);
}
private String computeDefaultValueClassName(String valueClassNameProp) {
@@ -81,7 +94,7 @@ public class JDBCConfiguration {
}
private Map<String, String> computeRegionToClassMap(String valueClassNameProp) {
- return parseMap(valueClassNameProp, v -> v);
+ return parseMap(valueClassNameProp, v -> v, false);
}
private boolean computeDefaultKeyPartOfValue(String keyPartOfValueProp) {
@@ -89,10 +102,11 @@ public class JDBCConfiguration {
}
private Map<String, Boolean> computeKeyPartOfValueMap(String keyPartOfValueProp) {
- return parseMap(keyPartOfValueProp, Boolean::parseBoolean);
+ return parseMap(keyPartOfValueProp, Boolean::parseBoolean, false);
}
- private <V> Map<String, V> parseMap(String propertyValue, Function<String, V> parser) {
+ private <V> Map<String, V> parseMap(String propertyValue, Function<String, V> parser,
+ boolean failOnNoSeparator) {
if (propertyValue == null) {
return null;
}
@@ -101,10 +115,18 @@ public class JDBCConfiguration {
for (String item : items) {
int idx = item.indexOf(getJdbcRegionSeparator());
if (idx == -1) {
+ if (failOnNoSeparator) {
+ throw new IllegalArgumentException(
+ item + " does not contain " + getJdbcRegionSeparator());
+ }
continue;
}
String regionName = item.substring(0, idx);
- String valueString = item.substring(idx + getJdbcRegionSeparator().length());;
+ String valueString = item.substring(idx + getJdbcRegionSeparator().length());
+ if (result.containsKey(regionName)) {
+ throw new IllegalArgumentException(
+ "Duplicate region name " + regionName + " is not allowed.");
+ }
result.put(regionName, parser.apply(valueString));
}
return result;
@@ -191,4 +213,14 @@ public class JDBCConfiguration {
return JDBC_REGION_SEPARATOR;
}
+ public String getTableForRegion(String regionName) {
+ if (this.regionToTableMap == null) {
+ return regionName;
+ }
+ String result = this.regionToTableMap.get(regionName);
+ if (result == null) {
+ result = regionName;
+ }
+ return result;
+ }
}
diff --git a/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCManager.java b/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCManager.java
index 9160207..33431a8 100644
--- a/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCManager.java
+++ b/geode-connectors/src/main/java/org/apache/geode/connectors/jdbc/internal/JDBCManager.java
@@ -415,8 +415,7 @@ public class JDBCManager {
}
private String getTableName(Region region) {
- // TODO: check config for mapping
- return region.getName();
+ return config.getTableForRegion(region.getName());
}
private void printResultSet(ResultSet rs) {
diff --git a/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCConfigurationUnitTest.java b/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCConfigurationUnitTest.java
index e524963..a76bde0 100644
--- a/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCConfigurationUnitTest.java
+++ b/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCConfigurationUnitTest.java
@@ -176,7 +176,6 @@ public class JDBCConfigurationUnitTest {
assertThat(config.getIsKeyPartOfValue("reg2")).isEqualTo(false);
}
-
public static class TestableJDBCConfiguration extends JDBCConfiguration {
public TestableJDBCConfiguration(Properties configProps) {
super(configProps);
@@ -187,4 +186,48 @@ public class JDBCConfigurationUnitTest {
return "->";
}
}
+
+ @Test
+ public void testDefaultRegionToTableMap() {
+ Properties props = new Properties();
+ props.setProperty("url", "");
+ JDBCConfiguration config = new JDBCConfiguration(props);
+ assertThat(config.getTableForRegion("foo")).isEqualTo("foo");
+ }
+
+ @Test
+ public void testRegionToTableMap() {
+ Properties props = new Properties();
+ props.setProperty("url", "");
+ props.setProperty("regionToTable", "reg1:table1");
+ JDBCConfiguration config = new JDBCConfiguration(props);
+ assertThat(config.getTableForRegion("reg1")).isEqualTo("table1");
+ }
+
+ @Test
+ public void testRegionsToTablesMap() {
+ Properties props = new Properties();
+ props.setProperty("url", "");
+ props.setProperty("regionToTable", "reg1:table1, reg2:table2");
+ JDBCConfiguration config = new JDBCConfiguration(props);
+ assertThat(config.getTableForRegion("reg1")).isEqualTo("table1");
+ assertThat(config.getTableForRegion("reg2")).isEqualTo("table2");
+ }
+
+ @Test(expected = IllegalArgumentException.class)
+ public void verifyRegionToTableThrows() {
+ Properties props = new Properties();
+ props.setProperty("url", "");
+ props.setProperty("regionToTable", "reg1:table1, reg2:table2, reg3");
+ new JDBCConfiguration(props);
+ }
+
+ @Test(expected = IllegalArgumentException.class)
+ public void verifyDuplicateRegionToTableThrows() {
+ Properties props = new Properties();
+ props.setProperty("url", "");
+ props.setProperty("regionToTable", "reg1:table1, reg2:table2, reg2:table3");
+ new JDBCConfiguration(props);
+ }
+
}
diff --git a/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCManagerUnitTest.java b/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCManagerUnitTest.java
index f0a260a..e8d560d 100644
--- a/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCManagerUnitTest.java
+++ b/geode-connectors/src/test/java/org/apache/geode/connectors/jdbc/internal/JDBCManagerUnitTest.java
@@ -105,13 +105,15 @@ public class JDBCManagerUnitTest {
private ResultSet tableResults;
private ResultSet primaryKeyResults;
private ResultSet queryResultSet;
+ private String tableName;
- TestableJDBCManagerWithResultSets(JDBCConfiguration config, ResultSet tableResults,
- ResultSet primaryKeyResults, ResultSet queryResultSet) {
+ TestableJDBCManagerWithResultSets(String tableName, JDBCConfiguration config,
+ ResultSet tableResults, ResultSet primaryKeyResults, ResultSet queryResultSet) {
super(config);
this.tableResults = tableResults;
this.primaryKeyResults = primaryKeyResults;
this.queryResultSet = queryResultSet;
+ this.tableName = tableName;
}
@Override
@@ -126,11 +128,11 @@ public class JDBCManagerUnitTest {
if (tableResults == null) {
tableResults = mock(ResultSet.class);
when(tableResults.next()).thenReturn(true, false);
- when(tableResults.getString("TABLE_NAME")).thenReturn(regionName.toUpperCase());
+ when(tableResults.getString("TABLE_NAME")).thenReturn(this.tableName.toUpperCase());
}
DatabaseMetaData metaData = mock(DatabaseMetaData.class);
- when(metaData.getPrimaryKeys(null, null, regionName.toUpperCase()))
+ when(metaData.getPrimaryKeys(null, null, this.tableName.toUpperCase()))
.thenReturn(primaryKeyResults);
when(metaData.getTables(any(), any(), any(), any())).thenReturn(tableResults);
@@ -165,15 +167,20 @@ public class JDBCManagerUnitTest {
public void tearDown() throws Exception {}
private void createManager(String... args) throws SQLException {
+ createManagerWithTableName(regionName, args);
+ }
+
+ private void createManagerWithTableName(String tableName, String... args) throws SQLException {
ResultSet rsKeys = mock(ResultSet.class);
when(rsKeys.next()).thenReturn(true, false);
when(rsKeys.getString("COLUMN_NAME")).thenReturn(ID_COLUMN_NAME);
ResultSet rs = mock(ResultSet.class);
when(rs.next()).thenReturn(true, false);
- when(rs.getString("TABLE_NAME")).thenReturn(regionName.toUpperCase());
+ when(rs.getString("TABLE_NAME")).thenReturn(tableName.toUpperCase());
- this.mgr = new TestableJDBCManagerWithResultSets(createConfiguration(args), rs, rsKeys, null);
+ this.mgr = new TestableJDBCManagerWithResultSets(tableName, createConfiguration(args), rs,
+ rsKeys, null);
}
private void createDefaultManager() throws SQLException {
@@ -190,8 +197,8 @@ public class JDBCManagerUnitTest {
private void createManager(ResultSet tableNames, ResultSet primaryKeys, ResultSet queryResultSet,
String... args) {
- this.mgr = new TestableJDBCManagerWithResultSets(createConfiguration(args), tableNames,
- primaryKeys, queryResultSet);
+ this.mgr = new TestableJDBCManagerWithResultSets(regionName, createConfiguration(args),
+ tableNames, primaryKeys, queryResultSet);
}
private JDBCConfiguration createConfiguration(String... args) {
@@ -604,6 +611,35 @@ public class JDBCManagerUnitTest {
any());
assertThat(fieldNameCaptor.getAllValues()).isEqualTo(Arrays.asList("id", "name", "age"));
assertThat(fieldValueCaptor.getAllValues()).isEqualTo(Arrays.asList("1", "Emp1", 21));
+ }
+
+ @Test
+ public void verifyRegionToTable() throws SQLException {
+ String tableName = "mySqlTable";
+ createManagerWithTableName(tableName, "regionToTable", regionName + ":" + tableName);
+ GemFireCacheImpl cache = Fakes.cache();
+ PdxInstanceFactory factory = mock(PdxInstanceFactory.class);
+ PdxInstance pi = mock(PdxInstance.class);
+ when(factory.create()).thenReturn(pi);
+ when(cache.createPdxInstanceFactory("no class", false)).thenReturn(factory);
+ Region region = Fakes.region(regionName, cache);
+ Object key = "1";
+ PdxInstance value = this.mgr.read(region, key);
+ ArgumentCaptor<String> sqlCaptor = ArgumentCaptor.forClass(String.class);
+ verify(this.connection).prepareStatement(sqlCaptor.capture());
+ assertThat(sqlCaptor.getValue())
+ .isEqualTo("SELECT * FROM " + tableName + " WHERE " + ID_COLUMN_NAME + " = ?");
+ ArgumentCaptor<Object> objectCaptor = ArgumentCaptor.forClass(Object.class);
+ verify(this.preparedStatement, times(1)).setObject(anyInt(), objectCaptor.capture());
+ List<Object> allObjects = objectCaptor.getAllValues();
+ assertThat(allObjects.get(0)).isEqualTo("1");
+ assertThat(value).isSameAs(pi);
+ ArgumentCaptor<String> fieldNameCaptor = ArgumentCaptor.forClass(String.class);
+ ArgumentCaptor<Object> fieldValueCaptor = ArgumentCaptor.forClass(Object.class);
+ verify(factory, times(2)).writeField(fieldNameCaptor.capture(), fieldValueCaptor.capture(),
+ any());
+ assertThat(fieldNameCaptor.getAllValues()).isEqualTo(Arrays.asList("name", "age"));
+ assertThat(fieldValueCaptor.getAllValues()).isEqualTo(Arrays.asList("Emp1", 21));
}
}
--
To stop receiving notification emails like this one, please contact
['"commits@geode.apache.org" <co...@geode.apache.org>'].