This is an automated email from the ASF dual-hosted git repository.
albumenj pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/dubbo.git
The following commit(s) were added to refs/heads/master by this push:
new 6acd5a2 fix #8378 parameter convert error (#8379)
6acd5a2 is described below
commit 6acd5a2a935c41c3f0b29ad9dce0d7e14586fded
Author: lmj <[email protected]>
AuthorDate: Sun Aug 15 22:18:00 2021 +0800
fix #8378 parameter convert error (#8379)
---
.../factory/annotation/ReferenceBeanBuilder.java | 19 ++-----
.../annotation/ServiceClassPostProcessor.java | 23 +-------
.../config/spring/util/DubboAnnotationUtils.java | 64 +++++++++++++++++++++-
.../factory/annotation/ParameterConvertTest.java | 60 ++++++++++++++++++++
4 files changed, 130 insertions(+), 36 deletions(-)
diff --git
a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ReferenceBeanBuilder.java
b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ReferenceBeanBuilder.java
index 7d61ec9..285e51a 100644
---
a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ReferenceBeanBuilder.java
+++
b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ReferenceBeanBuilder.java
@@ -16,12 +16,12 @@
*/
package org.apache.dubbo.config.spring.beans.factory.annotation;
-import org.apache.dubbo.common.utils.CollectionUtils;
import org.apache.dubbo.config.ConsumerConfig;
import org.apache.dubbo.config.MethodConfig;
import org.apache.dubbo.config.annotation.Method;
import org.apache.dubbo.config.annotation.Reference;
import org.apache.dubbo.config.spring.ReferenceBean;
+import org.apache.dubbo.config.spring.util.DubboAnnotationUtils;
import org.springframework.beans.propertyeditors.StringTrimmerEditor;
import org.springframework.context.ApplicationContext;
import org.springframework.core.annotation.AnnotationAttributes;
@@ -39,7 +39,6 @@ import static com.alibaba.spring.util.ObjectUtils.of;
import static
org.apache.dubbo.config.spring.util.DubboAnnotationUtils.resolveServiceInterfaceClass;
import static
org.apache.dubbo.config.spring.util.DubboBeanUtils.getOptionalBean;
import static org.springframework.core.annotation.AnnotationAttributes.fromMap;
-import static
org.springframework.util.StringUtils.commaDelimitedListToStringArray;
/**
* {@link ReferenceBean} Builder
@@ -124,19 +123,11 @@ class ReferenceBeanBuilder extends
AnnotatedInterfaceConfigBeanBuilder<Reference
dataBinder.registerCustomEditor(String.class, "listener", new
StringTrimmerEditor(true));
dataBinder.registerCustomEditor(Map.class, "parameters", new
PropertyEditorSupport() {
@Override
- public void setAsText(String text) throws
java.lang.IllegalArgumentException {
- // Trim all whitespace
- String content = StringUtils.trimAllWhitespace(text);
- if (!StringUtils.hasText(content)) { // No content , ignore
directly
- return;
+ public void setValue(Object value) {
+ if (value instanceof String[]) {
+ value = DubboAnnotationUtils.convertParameters((String[])
value);
}
- // replace "=" to ","
- content = StringUtils.replace(content, "=", ",");
- // replace ":" to ","
- content = StringUtils.replace(content, ":", ",");
- // String[] to Map
- Map<String, String> parameters =
CollectionUtils.toStringMap(commaDelimitedListToStringArray(content));
- setValue(parameters);
+ super.setValue(value);
}
});
diff --git
a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ServiceClassPostProcessor.java
b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ServiceClassPostProcessor.java
index 3181ca1..7997fc1 100644
---
a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ServiceClassPostProcessor.java
+++
b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/annotation/ServiceClassPostProcessor.java
@@ -18,7 +18,6 @@ package
org.apache.dubbo.config.spring.beans.factory.annotation;
import org.apache.dubbo.common.logger.Logger;
import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.common.utils.ArrayUtils;
import org.apache.dubbo.config.MethodConfig;
import org.apache.dubbo.config.annotation.DubboService;
import org.apache.dubbo.config.annotation.Method;
@@ -27,7 +26,7 @@ import org.apache.dubbo.config.spring.ServiceBean;
import
org.apache.dubbo.config.spring.context.DubboBootstrapApplicationListener;
import
org.apache.dubbo.config.spring.context.annotation.DubboClassPathBeanDefinitionScanner;
import org.apache.dubbo.config.spring.schema.AnnotationBeanDefinitionParser;
-
+import org.apache.dubbo.config.spring.util.DubboAnnotationUtils;
import org.springframework.beans.BeansException;
import org.springframework.beans.MutablePropertyValues;
import org.springframework.beans.factory.BeanClassLoaderAware;
@@ -62,10 +61,8 @@ import org.springframework.util.StringUtils;
import java.lang.annotation.Annotation;
import java.util.Collection;
import java.util.Collections;
-import java.util.HashMap;
import java.util.LinkedHashSet;
import java.util.List;
-import java.util.Map;
import java.util.Objects;
import java.util.Set;
@@ -414,7 +411,7 @@ public class ServiceClassPostProcessor implements
BeanDefinitionRegistryPostProc
// Set interface
builder.addPropertyValue("interface", interfaceClass.getName());
// Convert parameters into map
- builder.addPropertyValue("parameters",
convertParameters(serviceAnnotationAttributes.getStringArray("parameters")));
+ builder.addPropertyValue("parameters",
DubboAnnotationUtils.convertParameters(serviceAnnotationAttributes.getStringArray("parameters")));
// Add methods parameters
List<MethodConfig> methodConfigs =
convertMethodConfigs(serviceAnnotationAttributes.get("methods"));
if (!methodConfigs.isEmpty()) {
@@ -511,22 +508,6 @@ public class ServiceClassPostProcessor implements
BeanDefinitionRegistryPostProc
builder.addPropertyReference(propertyName, resolvedBeanName);
}
- private Map<String, String> convertParameters(String[] parameters) {
- if (ArrayUtils.isEmpty(parameters)) {
- return null;
- }
-
- if (parameters.length % 2 != 0) {
- throw new IllegalArgumentException("parameter attribute must be
paired with key followed by value");
- }
-
- Map<String, String> map = new HashMap<>();
- for (int i = 0; i < parameters.length; i += 2) {
- map.put(parameters[i], parameters[i + 1]);
- }
- return map;
- }
-
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory
beanFactory) throws BeansException {
diff --git
a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboAnnotationUtils.java
b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboAnnotationUtils.java
index 0a4d3ad..1c4e50d 100644
---
a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboAnnotationUtils.java
+++
b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboAnnotationUtils.java
@@ -16,13 +16,20 @@
*/
package org.apache.dubbo.config.spring.util;
+import org.apache.dubbo.common.utils.ArrayUtils;
+import org.apache.dubbo.common.utils.CollectionUtils;
import org.apache.dubbo.config.annotation.Reference;
import org.apache.dubbo.config.annotation.Service;
-
import org.springframework.core.annotation.AnnotationAttributes;
import org.springframework.util.Assert;
import org.springframework.util.ClassUtils;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
import static com.alibaba.spring.util.AnnotationUtils.getAttribute;
import static org.springframework.util.ClassUtils.getAllInterfacesForClass;
import static org.springframework.util.ClassUtils.resolveClassName;
@@ -147,4 +154,59 @@ public class DubboAnnotationUtils {
return interfaceName;
}
+
+ /**
+ * Resolve the parameters of {@link
org.apache.dubbo.config.annotation.DubboService}
+ * and {@link org.apache.dubbo.config.annotation.DubboReference} from the
specified.
+ * It iterate elements in order.The former element plays as key or
key&value role, it would be
+ * spilt if it contain specific string, for instance, ":" and "=". As for
later element can't
+ * be split in anytime.It will throw IllegalArgumentException If converted
array length isn't
+ * even number.
+ * The convert cases below work in right way,which are best practice.
+ * <p>
+ * (array->map)
+ * ["a","b"] ==> {a=b}
+ * [" a "," b "] ==> {a=b}
+ * ["a=b"] ==>{a=b}
+ * ["a:b"] ==>{a=b}
+ * ["a=b","c","d"] ==>{a=b,c=d}
+ * ["a","a:b"] ==>{a=a:b}
+ * </p>
+ *
+ * @param parameters
+ * @return
+ */
+ public static Map<String, String> convertParameters(String[] parameters) {
+ if (ArrayUtils.isEmpty(parameters)) {
+ return null;
+ }
+
+ List<String> compatibleParameterArray = Arrays.stream(parameters)
+ .map(String::trim)
+ .reduce(new ArrayList<>(parameters.length), (list, parameter)
->
+ {
+ if (list.size() % 2 == 1) {
+ //value doesn't split
+ list.add(parameter);
+ return list;
+ }
+
+ String[] sp1 = parameter.split(":");
+ if (sp1.length > 0 && sp1.length % 2 == 0) {
+ //key split
+
list.addAll(Arrays.stream(sp1).map(String::trim).collect(Collectors.toList()));
+ return list;
+ }
+ sp1 = parameter.split("=");
+ if (sp1.length > 0 && sp1.length % 2 == 0) {
+
list.addAll(Arrays.stream(sp1).map(String::trim).collect(Collectors.toList()));
+ return list;
+ }
+ list.add(parameter);
+ return list;
+ }
+ , (a, b) -> a);
+
+ return
CollectionUtils.toStringMap(compatibleParameterArray.toArray(new String[0]));
+ }
}
diff --git
a/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/beans/factory/annotation/ParameterConvertTest.java
b/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/beans/factory/annotation/ParameterConvertTest.java
new file mode 100644
index 0000000..d32e4ec
--- /dev/null
+++
b/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/beans/factory/annotation/ParameterConvertTest.java
@@ -0,0 +1,60 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF 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 org.apache.dubbo.config.spring.beans.factory.annotation;
+
+import org.apache.dubbo.config.spring.util.DubboAnnotationUtils;
+import org.junit.jupiter.api.Assertions;
+import org.junit.jupiter.api.Test;
+import org.springframework.test.annotation.DirtiesContext;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * {@link DubboAnnotationUtils#convertParameters} Test
+ */
+@DirtiesContext(classMode = DirtiesContext.ClassMode.AFTER_EACH_TEST_METHOD)
+public class ParameterConvertTest {
+
+ @Test
+ public void test() {
+ /**
+ * (array->map)
+ * ["a","b"] ==> {a=b}
+ * [" a "," b "] ==> {a=b}
+ * ["a=b"] ==>{a=b}
+ * ["a:b"] ==>{a=b}
+ * ["a=b","c","d"] ==>{a=b,c=d}
+ * ["a=b","c:d"] ==>{a=b,c=d}
+ * ["a","a:b"] ==>{a=a:b}
+ */
+ Map<String, String> parametersMap = new HashMap<>();
+ parametersMap.put("a", "b");
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{"a", "b"}));
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{" a ", " b "}));
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{"a=b"}));
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{"a:b"}));
+
+ parametersMap.put("c", "d");
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{"a=b", "c", "d"}));
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{"a:b", "c=d"}));
+
+ parametersMap.clear();
+ parametersMap.put("a", "a:b");
+ Assertions.assertEquals(parametersMap,
DubboAnnotationUtils.convertParameters(new String[]{"a", "a:b"}));
+ }
+}