package com.alibaba.cobar.client.router.rules;
import static org.testng.AssertJUnit.assertEquals;
import static org.testng.AssertJUnit.assertFalse;
import static org.testng.AssertJUnit.assertTrue;
import static org.testng.AssertJUnit.fail;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.apache.commons.lang.ArrayUtils;
import org.testng.annotations.AfterMethod;
import org.testng.annotations.BeforeMethod;
import org.testng.annotations.Test;
import com.alibaba.cobar.client.entities.Tweet;
import com.alibaba.cobar.client.router.rules.ibatis.IBatisSqlActionShardingRule;
import com.alibaba.cobar.client.router.rules.support.ModFunction;
import com.alibaba.cobar.client.router.support.IBatisRoutingFact;
import com.alibaba.cobar.client.support.utils.CollectionUtils;
/**
* TODO Comment of IBatisSqlActionShardingRuleTest
*
* @author fujohnwang
* @see {@link IBatisNamespaceShardingRuleTest} for more test scenarios.
*/
@Test
public class IBatisSqlActionShardingRuleTest{
// almost copied from IBatisNamespaceShardingRuleTest, although a same top class is better.
public static final String DEFAULT_TYPE_PATTEN = "com.alibaba.cobar.client.entity.Tweet.create";
public static final String DEFAULT_SHARDING_PATTERN = "id>=10000 and id < 20000";
public static final String[] DEFAULT_SHARDS = { "shard1", "shard2" };
private IBatisSqlActionShardingRule rule;
@BeforeMethod
protected void setUp() throws Exception {
rule = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN, "shard1,shard2",
DEFAULT_SHARDING_PATTERN);
}
@AfterMethod
protected void tearDown() throws Exception {
rule = null;
}
public void testSqlActionShardingRuleConstructionAbnormally() {
try {
rule = new IBatisSqlActionShardingRule(null, "shard1,shard2", DEFAULT_SHARDING_PATTERN);
fail();
} catch (IllegalArgumentException e) {
// pass
}
try {
rule = new IBatisSqlActionShardingRule("", "shard1,shard2", DEFAULT_SHARDING_PATTERN);
fail();
} catch (IllegalArgumentException e) {
// pass
}
try {
rule = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN, "",
DEFAULT_SHARDING_PATTERN);
fail();
} catch (IllegalArgumentException e) {
// pass
}
try {
rule = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN, null,
DEFAULT_SHARDING_PATTERN);
fail();
} catch (IllegalArgumentException e) {
// pass
}
try {
rule = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN, "shard1,shard2", null);
fail();
} catch (IllegalArgumentException e) {
// pass
}
try {
rule = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN, "shard1,shard2", "");
fail();
} catch (IllegalArgumentException e) {
// pass
}
}
public void testSqlActionShardingRulePatternMatchingNormally() {
Tweet t = new Tweet();
t.setId(15000L);
t.setTweet("anything");
IBatisRoutingFact fact = new IBatisRoutingFact(
"com.alibaba.cobar.client.entity.Tweet.create", t);
assertTrue(rule.isDefinedAt(fact));
List<String> shards = rule.action();
assertTrue(CollectionUtils.isNotEmpty(shards));
assertEquals(2, shards.size());
for (String shard : shards) {
assertTrue(ArrayUtils.contains(DEFAULT_SHARDS, shard));
}
fact = new IBatisRoutingFact("com.alibaba.cobar.client.entity.Tweet.update", t);
assertFalse(rule.isDefinedAt(fact));
t.setId(20000L);
fact = new IBatisRoutingFact("com.alibaba.cobar.client.entity.Tweet.create", t);
assertFalse(rule.isDefinedAt(fact));
fact = new IBatisRoutingFact("com.alibaba.cobar.client.entity.Tweet.create", null);
assertFalse(rule.isDefinedAt(fact));
fact = new IBatisRoutingFact("com.alibaba.cobar.client.entity.Tweet.create", new Object());
assertFalse(rule.isDefinedAt(fact));
}
public void testSqlActionShardingRulePatternMatchingAbnormally() {
try {
rule.setActionPatternSeparator(null);
fail();
} catch (IllegalArgumentException e) {
// pass
}
try {
rule.isDefinedAt(null);
fail();
} catch (IllegalArgumentException e) {
// pass
}
}
public void testSqlActionShardingRuleWithCustomFunctions() {
IBatisSqlActionShardingRule r = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN,
"shard1,shard2", "mod.apply(id)==3");
Map<String, Object> functions = new HashMap<String, Object>();
functions.put("mod", new ModFunction(18L));
r.setFunctionMap(functions);
Tweet t = new Tweet();
t.setId(21L);
t.setTweet("anything");
IBatisRoutingFact fact = new IBatisRoutingFact(
"com.alibaba.cobar.client.entity.Tweet.create", t);
assertTrue(r.isDefinedAt(fact));
}
public void testSqlActionShardingRuleWithSimpleContextObjectType(){
IBatisSqlActionShardingRule r = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN,
"shard1", "$ROOT.startsWith(\"J\")");
IBatisRoutingFact fact = new IBatisRoutingFact(
"com.alibaba.cobar.client.entity.Tweet.create", "Jack");
assertTrue(r.isDefinedAt(fact));
r = new IBatisSqlActionShardingRule(DEFAULT_TYPE_PATTEN,
"shard1", "startsWith(\"J\")");
assertTrue(r.isDefinedAt(fact));
fact = new IBatisRoutingFact(
"com.alibaba.cobar.client.entity.Tweet.create", "Amanda");
assertFalse(r.isDefinedAt(fact));
}
}