Search code examples
javaregexreflection

Java method using reflection and matcher


I need a method that takes 2 parameters:

The template parameter can be : Hi ${name}, There's been ${days} days since you logged in on ${site}. The object parameter its an object for example: Site site = new Site("Alex",100,"google");

If ${ xxx } is found then i need to replace with the getMethod from Object

So if we call the method needs to return Hello Alex , There's been 100 days since you logged in on Google.

this is what i have:

public static String metodaex2(String template, Object object)
        throws IllegalAccessException, IllegalArgumentException,
        InvocationTargetException {

    Class<?> clasa = object.getClass();
    Method[] methodsArray = clasa.getDeclaredMethods();

    StringBuffer sb = new StringBuffer();
    Object methodReturn = null;
    Set<Object> listObjects = new TreeSet<Object>(new ObjectsComparator());
    for (Method m : methodsArray ){
        //a method that finds a getter
        if (isGetter(m)) {
            //add to the list all get methods
            methodReturn = m.invoke(object);
            listObjects.add(methodReturn);
        }

    }
    String pattern1 = "${";
    String pattern2 = "}";

    Pattern p = Pattern.compile(Pattern.quote(pattern1) + "(.*?)"
            + Pattern.quote(pattern2));
    Matcher matcher = p.matcher(template);

    while (matcher.find()) {
             System.out.println(matcher.group(1)); /
         matcher.appendReplacement(sb, matcher.group(1));

    }
    return sb.toString();
}

But i dont know how to make the actual replacement. Please help


Solution

  • Here are some trails you could use to do such a job.

    Read an object's property value given its name:

    public static Object readProperty(String name, Object object) throws Exception {
        Class<?> clazz = object.getClass();
        do {
            try {
                Field field = clazz.getDeclaredField(name);
                return field.get(object);
            } catch (NoSuchFieldException e) {
                clazz = clazz.getSuperclass();
            }
        } while (clazz != null);
        return null;
    }
    

    Regex matching your pattern, capturing the property name (visualization by Debuggex):

    \$\{([^}]+)\}
    

    Regular expression visualization

    Iterating over matches in Java:

        String input = "Hi ${name}, There's been ${days} days since you logged in on ${site}.";
        String regex = "\\$\\{([^}]+)\\}";
    
        Pattern pattern = Pattern.compile(regex);
        Matcher matcher = pattern.matcher(input);
        while (matcher.find()) {
            String name = matcher.group(1);
            // name contains now the property name
            // add the logic here: replace occurrences of "${" + name + "}" by the real value
        }