Skip to content

Commit

Permalink
完善前缀匹配逻辑
Browse files Browse the repository at this point in the history
  • Loading branch information
seaswalker committed Apr 12, 2017
1 parent 863c160 commit 8e7445c
Show file tree
Hide file tree
Showing 14 changed files with 108 additions and 43 deletions.
4 changes: 4 additions & 0 deletions etc/test.xml
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,8 @@
<leader>li</leader>
<leader>hu</leader>
</leaders>
<province>
<city1>jinan</city1>
<city2>qingdao</city2>
</province>
</china>
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

<groupId>skywalker</groupId>
<artifactId>Configurer</artifactId>
<version>1.1-SNAPSHOT</version>
<version>1.2-SNAPSHOT</version>
<build>
<plugins>
<plugin>
Expand Down
31 changes: 25 additions & 6 deletions src/main/java/configurator/bean/BeanContainer.java
Original file line number Diff line number Diff line change
Expand Up @@ -548,12 +548,12 @@ private Object resolveConfByValue(AnnotatedElement object, String name, Class cl
throw new IllegalStateException("Key must be confirmed: " + object + ".");
}
}
if (isRequireAll(key)) {
if (needFind(key)) {
if (!isEligibleMap(clazz, type)) {
throw new IllegalStateException("Inject all configurations for " + object +
" failed, type Map<String,String> required.");
}
result = source.getAll();
result = source.find(handlePrefix(key));
} else {
if (!source.contains(key)) {
String defaultValue = value.defaultValue();
Expand Down Expand Up @@ -594,14 +594,33 @@ private Object convertTo(String value, Class requiredType) {
}

/**
* 字段是否需要{@link Source}的所有配置.
* 是否需要进行前缀搜索.
*
* @return true, 如果需要
*/
private boolean needFind(String key) {
String[] parts = key.split("\\.");
return (parts[parts.length - 1].equals("*"));
}

/**
* 将(a.b.*)处理为(a.b).
*/
private boolean isRequireAll(String key) {
return (key.equals("*"));
private String handlePrefix(String key) {
String[] parts = key.split("\\.");
if (parts.length == 1) {
return "";
} else {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < parts.length - 1; i++) {
sb.append(parts[i]).append(".");
}
return sb.deleteCharAt(sb.length() - 1).toString();
}
}

/**
* 给定的字段是否是{@link Map},且泛型满足{@link Source}.getAll()方法的返回值.
* 给定的字段是否是{@link Map},且泛型满足{@link Source}.find()方法的返回值.
*
* @return true,如果满足
*/
Expand Down
16 changes: 15 additions & 1 deletion src/main/java/configurator/conf/AbstractSource.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
package configurator.conf;

import configurator.util.Util;

import java.util.Map;

/**
* {@link Source}骨架实现,提供统一的{@link Source#contains(String)}方法实现.
*
Expand Down Expand Up @@ -54,7 +58,17 @@ public String[] getStringArray(String key, String separator) {

@Override
public String[] getStringArray(String key) {
return null;
throw new UnsupportedOperationException();
}

@Override
public final Map<String, String> find(String prefix) {
if (Util.isEmpty(prefix) || prefix.equals("*")) {
prefix = "";
}
return doFind(prefix);
}

protected abstract Map<String, String> doFind(String prefix);

}
4 changes: 2 additions & 2 deletions src/main/java/configurator/conf/AbstractTreeBasedSource.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@ protected AbstractTreeBasedSource(String path) {
}

@Override
public Map<String, String> getAll() {
return holder.getAll();
protected final Map<String, String> doFind(String prefix) {
return holder.find(prefix);
}

}
4 changes: 2 additions & 2 deletions src/main/java/configurator/conf/CompositeSource.java
Original file line number Diff line number Diff line change
Expand Up @@ -54,10 +54,10 @@ public String[] getStringArray(String key) {
}

@Override
public Map<String, String> getAll() {
protected Map<String, String> doFind(String prefix) {
LinkedHashMap<String, String> result = new LinkedHashMap<>();
for (int i = 0, l = sources.size(); i < l; i++) {
result.putAll(sources.get(i).getAll());
result.putAll(sources.get(i).find(prefix));
}
return result;
}
Expand Down
20 changes: 15 additions & 5 deletions src/main/java/configurator/conf/JsonSource.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import configurator.conf.exception.LoadException;
import configurator.util.Util;

import java.io.IOException;
import java.math.BigDecimal;
Expand Down Expand Up @@ -33,7 +34,7 @@ public void load() throws LoadException {
String data = readAsString();
Object o = JSON.parse(data);
if (!(o instanceof JSONObject)) {
throw new IllegalStateException("We support configurator.json object only.");
throw new IllegalStateException("We support json object only.");
}
json = JSONObject.class.cast(o);
} catch (Exception e) {
Expand Down Expand Up @@ -98,7 +99,7 @@ private JSONObject seekTo(String[] parts) {
for (int i = 0, l = parts.length; i < l; i++) {
Object o = node.get(parts[i]);
if (o == null) {
throw new IllegalStateException("Can't find key: " + concatParts(parts, i) + ".");
return null;
}
if (!(o instanceof JSONObject)) {
throw new IllegalStateException("Key: " + concatParts(parts, i) + " can't be leaf or array node.");
Expand Down Expand Up @@ -154,7 +155,7 @@ public String[] getStringArray(String key, String separator) {
public String[] getStringArray(String key) {
Object o = doGet(key);
if (!(o instanceof JSONArray)) {
throw new IllegalStateException("Given key: " + key + " must be a configurator.json array.");
throw new IllegalStateException("Given key: " + key + " must be a json array.");
}
JSONArray array = JSONArray.class.cast(o);
if (!isPrimitiveArray(array)) {
Expand All @@ -165,9 +166,18 @@ public String[] getStringArray(String key) {
}

@Override
public Map<String, String> getAll() {
protected Map<String, String> doFind(String prefix) {
Map<String, String> result = new LinkedHashMap<>();
collect(result, "", json);
JSONObject parent;
if (prefix.equals("")) {
parent = json;
} else {
parent = seekTo(prefix.split("\\."));
prefix += ".";
}
if (parent != null) {
collect(result, prefix, parent);
}
return result;
}

Expand Down
5 changes: 3 additions & 2 deletions src/main/java/configurator/conf/Source.java
Original file line number Diff line number Diff line change
Expand Up @@ -62,10 +62,11 @@ public interface Source {
String[] getStringArray(String key);

/**
* 以{@link Map}的形式得到所有的配置.
* 属性搜索.
*
* @param prefix 前缀,比如为a.b,那么将得到a.b下所有的子属性的值,如果为null或"",那么表示获取当前Source下的所有属性.
* @return {@link Map}
*/
Map<String, String> getAll();
Map<String, String> find(String prefix);

}
36 changes: 16 additions & 20 deletions src/main/java/configurator/conf/TrieTree.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package configurator.conf;

import configurator.util.Util;

import java.util.LinkedHashMap;
import java.util.Map;

Expand Down Expand Up @@ -91,7 +93,7 @@ public String get(String key) {
return null;
}
if (!isLeaf(node)) {
throw new IllegalStateException("Get() method supports leaf node only.");
throw new IllegalStateException("Get() method supports leaf node only, key '" + key + "'.");
}
return node.value;
}
Expand All @@ -115,21 +117,13 @@ public String getMetaData(String key, String metaDataKey) {
*/
public Map<String, String> find(String prefix) {
Node node = seekTo(prefix);
if (node == null) {
return new LinkedHashMap<>(0);
Map<String, String> result = new LinkedHashMap<>(0);
if (node != null) {
if (node != head) {
prefix += ".";
}
collectAsMap(prefix, node, result);
}
Map<String, String> result = new LinkedHashMap<>();
prefix += ".";
collectAsMap(prefix, node, result);
return result;
}

/**
* 得到当前树中的所有节点.
*/
public Map<String, String> getAll() {
Map<String, String> result = new LinkedHashMap<>();
collectAsMap("", head, result);
return result;
}

Expand Down Expand Up @@ -168,12 +162,14 @@ private boolean hasMeta(Node node) {
* 向下对key逐部分进行匹配.
*/
private Node seekTo(String key) {
String[] parts = key.split(separator);
Node node = head;
for (int i = 0, l = parts.length; i < l; i++) {
node = findChild(node, parts[i]);
if (node == null) {
return null;
if (!key.equals("")) {
String[] parts = key.split(separator);
for (int i = 0, l = parts.length; i < l; i++) {
node = findChild(node, parts[i]);
if (node == null) {
return null;
}
}
}
return node;
Expand Down
13 changes: 13 additions & 0 deletions src/test/java/configurator/ioc/Teacher.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@
import configurator.bean.BeanContainer;
import configurator.bean.BeanContainerAware;
import configurator.bean.annotation.Component;
import configurator.bean.annotation.Value;

import java.util.Map;

/**
* 老师.
Expand All @@ -12,10 +15,20 @@
@Component
public class Teacher implements BeanContainerAware {

@Value(key = "*")
private Map<String, String> all;


@Override
public void setBeanContainer(BeanContainer beanContainer) {
System.out.println("setBeanContainer调用");
}

@Override
public String toString() {
return "Teacher{" +
"all=" + all +
'}';
}

}
5 changes: 4 additions & 1 deletion src/test/java/configurator/json/JsonHolder.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import configurator.bean.annotation.Value;

import java.util.Arrays;
import java.util.Map;

/**
* configurator.conf.json载体.
Expand All @@ -30,6 +31,8 @@ public class JsonHolder {
private String[] msisdns;
@Value(key = "loc_ids")
private String[] locIds;
@Value(key = "interval.*")
private Map<String, String> interval;

@Value
public void setIp(String ip) {
Expand All @@ -48,7 +51,7 @@ public String toString() {
", intervalValue=" + intervalValue +
", msisdns=" + Arrays.toString(msisdns) +
", locIds=" + Arrays.toString(locIds) +
", interval=" + interval +
'}';
}

}
7 changes: 6 additions & 1 deletion src/test/java/configurator/properties/DB.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
import configurator.bean.annotation.Component;
import configurator.bean.annotation.Value;

import java.util.Map;

@Component
public class DB {

Expand All @@ -12,13 +14,16 @@ public class DB {
private int password;
@Value(key = "db.name")
private String dbName;
@Value(key = "db.*")
private Map<String, String> all;

@Override
public String toString() {
return "DB{" +
"username='" + username + '\'' +
", password='" + password + '\'' +
", password=" + password +
", dbName='" + dbName + '\'' +
", all=" + all +
'}';
}

Expand Down
2 changes: 1 addition & 1 deletion src/test/java/configurator/trietree/TrieTreeTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ public void all() {
tree.addValue("us.leader", "Obama");
tree.addMetaData("us.leader", "color", "black");
tree.addMetaData("china.leader", "color", "yellow");
System.out.println(tree.getAll());
System.out.println(tree.find(""));
}

/**
Expand Down
2 changes: 1 addition & 1 deletion src/test/java/configurator/xml/Reporter.java
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ public void setDomain(String domain) {
this.domain = domain;
}

@Value(key = "*")
@Value(key = "china.province.*")
public void setAll(HashMap<Object, String> all) {
this.all = all;
}
Expand Down

0 comments on commit 8e7445c

Please sign in to comment.