package org.restler.spring.mvc;

import org.objectweb.asm.ClassReader;
import org.restler.client.RestlerException;
import org.restler.spring.mvc.asm.ClassUtils;
import org.restler.spring.mvc.asm.ParameterNameDiscoveringVisitor;

import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Member;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

public class ParameterNameDiscoverer {

    public String[] getParameterNames(Method method) {
        String[] result = getParameterNamesDefault(method);

        if(result == null) {
            result = getParameterNamesFromLocalVariableTable(method);
        }

        return result;
    }

    private String[] getParameterNamesDefault(Method method) {
        Parameter[] parameters = method.getParameters();
        String[] parameterNames = new String[parameters.length];
        for (int i = 0; i < parameters.length; i++) {
            Parameter param = parameters[i];
            if (!param.isNamePresent()) {
                return null;
            }
            parameterNames[i] = param.getName();
        }
        return parameterNames;
    }

    private String[] getParameterNamesFromLocalVariableTable(Method method) {
        Class<?> declaringClass = method.getDeclaringClass();

        Map<Member, String[]> map = inspectClass(declaringClass);

        if (map != null) {
            return map.get(method);
        }
        return null;
    }

    private Map<Member, String[]> inspectClass(Class<?> clazz) {
        InputStream inputStream = clazz.getResourceAsStream(ClassUtils.getClassFileName(clazz));
        if (inputStream == null) {
            return null;
        }
        try {
            ClassReader classReader = new ClassReader(inputStream);
            Map<Member, String[]> map = new ConcurrentHashMap<>(32);
            classReader.accept(new ParameterNameDiscoveringVisitor(clazz, map), 0);
            return map;
        }
        catch (IOException e) {
            throw new RestlerException("Can't read class from stream.", e);
        }
        catch(IllegalArgumentException e) {
            throw new RestlerException("Illegal argument.", e);
        }
        finally {
            try {
                inputStream.close();
            }
            catch (IOException ex) {
                // ignore
            }
        }
    }
}

@@ -397,16 +397,20 @@
 va.util.
+Hash
 Map;%0Aimp
@@ -427,33 +427,8 @@
 til.
-concurrent.ConcurrentHash
 Map;
@@ -1573,16 +1573,20 @@
         
+try(
 InputStr
@@ -1664,26 +1664,30 @@
 (clazz))
-;%0A
+) %7B%0A  
         
 if (inpu
@@ -1674,24 +1674,26 @@
 %7B%0A          
+  
 if (inputStr
@@ -1711,32 +1711,36 @@
 ) %7B%0A            
+    
 return null;%0A   
@@ -1748,23 +1748,14 @@
     
-%7D%0A
     
-    try %7B
+%7D%0A
 %0A   
@@ -1867,18 +1867,8 @@
 new 
-Concurrent
 Hash
@@ -2236,182 +2236,8 @@
   %7D%0A
-        finally %7B%0A            try %7B%0A                inputStream.close();%0A            %7D%0A            catch (IOException ex) %7B%0A                // ignore%0A            %7D%0A        %7D%0A
     

Change ConcurrentHashMap to HashMap.