zhouhao %!s(int64=2) %!d(string=hai) anos
pai
achega
9b4280ade1

+ 7 - 0
hsweb-core/src/main/java/org/hswebframework/web/bean/ClassDescription.java

@@ -15,6 +15,8 @@ public class ClassDescription {
     private final boolean enumDict;
     private final int fieldSize;
 
+    private final Object[] enums;
+
     public ClassDescription(Class<?> type) {
         this.type = type;
         collectionType = Collection.class.isAssignableFrom(type);
@@ -22,6 +24,11 @@ public class ClassDescription {
         arrayType = type.isArray();
         enumType = type.isEnum();
         fieldSize = type.getDeclaredFields().length;
+        if (enumType) {
+            enums = type.getEnumConstants();
+        } else {
+            enums = null;
+        }
     }
 
 }

+ 2 - 2
hsweb-core/src/main/java/org/hswebframework/web/bean/ClassDescriptions.java

@@ -1,12 +1,12 @@
 package org.hswebframework.web.bean;
 
-import org.jctools.maps.NonBlockingHashMap;
 
 import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
 
 public class ClassDescriptions {
 
-    private static final Map<Class<?>, ClassDescription> CACHE = new NonBlockingHashMap<>();
+    private static final Map<Class<?>, ClassDescription> CACHE = new ConcurrentHashMap<>();
 
     public static ClassDescription getDescription(Class<?> type) {
         return CACHE.computeIfAbsent(type, ClassDescription::new);

+ 31 - 9
hsweb-core/src/main/java/org/hswebframework/web/bean/FastBeanCopier.java

@@ -14,6 +14,7 @@ import org.hswebframework.web.proxy.Proxy;
 import org.jctools.maps.NonBlockingHashMap;
 import org.springframework.core.ResolvableType;
 import org.springframework.util.ClassUtils;
+import org.springframework.util.CollectionUtils;
 import org.springframework.util.ReflectionUtils;
 
 import java.beans.PropertyDescriptor;
@@ -88,6 +89,9 @@ public final class FastBeanCopier {
     }
 
     public static Object getProperty(Object source, String key) {
+        if (source instanceof Map) {
+            return ((Map<?, ?>) source).get(key);
+        }
         SingleValueMap<Object, Object> map = new SingleValueMap<>();
         copy(source, map, include(key));
         return map.getValue();
@@ -117,7 +121,16 @@ public final class FastBeanCopier {
     @SuppressWarnings("all")
     public static <T, S> T copy(S source, T target, Converter converter, Set<String> ignore) {
         if (source instanceof Map && target instanceof Map) {
-            ((Map) target).putAll(((Map) source));
+            if (CollectionUtils.isEmpty(ignore)) {
+                ((Map) target).putAll(((Map) source));
+            } else {
+                ((Map) source)
+                        .forEach((k, v) -> {
+                            if (!ignore.contains(k)) {
+                                ((Map) target).put(k, v);
+                            }
+                        });
+            }
             return target;
         }
 
@@ -584,20 +597,29 @@ public final class FastBeanCopier {
             if (target.isEnumType()) {
                 if (target.isEnumDict()) {
                     String strVal = String.valueOf(source);
-
-                    Object val = EnumDict.find((Class) targetClass, e -> {
-                        return e.eq(source) || e.name().equalsIgnoreCase(strVal);
-                    }).orElse(null);
+                    Object val = null;
+                    for (Object anEnum : target.getEnums()) {
+                        EnumDict dic = ((EnumDict) anEnum);
+                        Enum e = ((Enum<?>) anEnum);
+                        if (dic.eq(source) || e.name().equalsIgnoreCase(strVal)) {
+                            val = (T) anEnum;
+                            break;
+                        }
+                    }
+                    if (val == null) {
+                        return null;
+                    }
                     if (targetClass.isInstance(val)) {
                         return ((T) val);
                     }
                     return convert(val, targetClass, genericType);
                 }
                 String strSource = String.valueOf(source);
-                for (T t : targetClass.getEnumConstants()) {
-                    if (((Enum) t).name().equalsIgnoreCase(strSource)
-                            || Objects.equals(String.valueOf(((Enum<?>) t).ordinal()), strSource)) {
-                        return t;
+                for (Object e : target.getEnums()) {
+                    Enum t = ((Enum<?>) e);
+                    if ((t.name().equalsIgnoreCase(strSource)
+                            || Objects.equals(String.valueOf(t.ordinal()), strSource))) {
+                        return (T)e;
                     }
                 }
 

+ 3 - 3
hsweb-core/src/main/java/org/hswebframework/web/bean/SingleValueMap.java

@@ -28,7 +28,7 @@ public class SingleValueMap<K, V> implements Map<K, V> {
 
     @Override
     public V get(Object key) {
-        return null;
+        return Objects.equals(key, this.key) ? value : null;
     }
 
     @Override
@@ -50,9 +50,9 @@ public class SingleValueMap<K, V> implements Map<K, V> {
     }
 
     @Override
-    public void putAll(Map<? extends K,? extends V> m) {
+    public void putAll(Map<? extends K, ? extends V> m) {
         if (m.size() > 0) {
-            Map.Entry<? extends K,? extends V> entry = m.entrySet().iterator().next();
+            Map.Entry<? extends K, ? extends V> entry = m.entrySet().iterator().next();
             this.key = entry.getKey();
             this.value = entry.getValue();
         }

+ 16 - 8
hsweb-core/src/main/java/org/hswebframework/web/dict/EnumDict.java

@@ -19,6 +19,8 @@ import lombok.AllArgsConstructor;
 import lombok.NoArgsConstructor;
 import lombok.SneakyThrows;
 import lombok.extern.slf4j.Slf4j;
+import org.hswebframework.web.bean.ClassDescription;
+import org.hswebframework.web.bean.ClassDescriptions;
 import org.hswebframework.web.exception.ValidationException;
 import org.hswebframework.web.i18n.LocaleUtils;
 import org.springframework.beans.BeanUtils;
@@ -135,20 +137,25 @@ public interface EnumDict<V> extends JSONSerializable {
      * @param <T>       枚举类型
      * @return 查找到的结果
      */
+    @SuppressWarnings("all")
     static <T extends Enum & EnumDict> Optional<T> find(Class<T> type, Predicate<T> predicate) {
-        if (type.isEnum()) {
-            for (T enumDict : type.getEnumConstants()) {
-                if (predicate.test(enumDict)) {
-                    return Optional.of(enumDict);
+        ClassDescription description = ClassDescriptions.getDescription(type);
+        if (description.isEnumType()) {
+            for (Object enumDict : description.getEnums()) {
+                if (predicate.test((T) enumDict)) {
+                    return Optional.of((T) enumDict);
                 }
             }
         }
         return Optional.empty();
     }
 
+    @SuppressWarnings("all")
     static <T extends Enum & EnumDict> List<T> findList(Class<T> type, Predicate<T> predicate) {
-        if (type.isEnum()) {
-            return Arrays.stream(type.getEnumConstants())
+        ClassDescription description = ClassDescriptions.getDescription(type);
+        if (description.isEnumType()) {
+            return Arrays.stream(description.getEnums())
+                         .map(v -> (T) v)
                          .filter(predicate)
                          .collect(Collectors.toList());
         }
@@ -199,7 +206,8 @@ public interface EnumDict<V> extends JSONSerializable {
 
     @SafeVarargs
     static <T extends Enum & EnumDict> boolean in(T target, T... t) {
-        Enum[] all = target.getClass().getEnumConstants();
+        ClassDescription description= ClassDescriptions.getDescription(target.getClass());
+        Object[] all = description.getEnums();
 
         if (all.length >= 64) {
             List<T> list = Arrays.asList(t);
@@ -385,7 +393,7 @@ public interface EnumDict<V> extends JSONSerializable {
                             return e.name();
                         }).collect(Collectors.toList());
 
-                return new ValidationException(currentName,"validation.parameter_does_not_exist_in_enums", currentName);
+                return new ValidationException(currentName, "validation.parameter_does_not_exist_in_enums", currentName);
             };
             if (EnumDict.class.isAssignableFrom(findPropertyType) && findPropertyType.isEnum()) {
                 if (node.isObject()) {

+ 9 - 0
hsweb-core/src/test/java/org/hswebframework/web/bean/FastBeanCopierTest.java

@@ -1,5 +1,7 @@
 package org.hswebframework.web.bean;
 
+import com.google.common.collect.ImmutableMap;
+import jdk.nashorn.internal.objects.annotations.Getter;
 import org.junit.Assert;
 import org.junit.Test;
 
@@ -113,6 +115,13 @@ public class FastBeanCopierTest {
         Assert.assertEquals(reference.get(),source.getName());
     }
 
+    @Test
+    public void testGetProperty(){
+
+        Assert.assertEquals(1,FastBeanCopier.getProperty(ImmutableMap.of("a",1,"b",2),"a"));
+
+    }
+
 
     public interface ProxyTest {
         String getName();