All Downloads are FREE. Search and download functionalities are using the official Maven repository.

net.wpm.codegen.ClassScope Maven / Gradle / Ivy

The newest version!
/*
 * Copyright (C) 2015 SoftIndex LLC.
 *
 * Licensed 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 net.wpm.codegen;


import java.lang.reflect.Constructor;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.objectweb.asm.commons.Method;

/**
 * Represents the scope of a new class.
 * Inspired by reflectasm.
 * 
 * @author Nico Hezel
 */
public class ClassScope {

	private final Class mainType;
	private final Set> parentClasses = new LinkedHashSet<>();
	
	private final Map> fields = new LinkedHashMap<>();
	private final Map> staticFields = new LinkedHashMap<>();
	private final List constructors = new ArrayList<>();
	private final Set methods = new LinkedHashSet<>();
	private final Set staticMethods = new LinkedHashSet<>();
	

	/**
	 * Collect all non-private methods and fields of the given classes.
	 * 
	 * @param mainType might be a super class
	 * @param types might be interfaces 
	 */
	public ClassScope(Class mainType, List> types) {
		this.mainType = mainType;
		
	    collectMembers(mainType);
	    for (Class type : types)
	    	if(type.isInterface())
	    		collectMembers(type);
	}

	 private void addNonPrivateField(java.lang.reflect.Field[] arr) {
	        for(java.lang.reflect.Field e : arr) {
	            if(Modifier.isPrivate(e.getModifiers())) continue;
	            
	            if(Modifier.isStatic(e.getModifiers()))
	            	staticFields.put(e.getName(), e.getType());
	            else
	            	fields.put(e.getName(), e.getType());
	        }
	    }
	 
    private void addNonPrivateMethod(java.lang.reflect.Method[] arr) {
        for(java.lang.reflect.Method e : arr) {
            if(Modifier.isPrivate(e.getModifiers())) continue;
            
            if(Modifier.isStatic(e.getModifiers()))
            	staticMethods.add(Method.getMethod(e));
            else
            	methods.add(Method.getMethod(e));
        }
    }

    private void recursiveAddInterfaceMethodsToList(Class interfaceType) {
    	addNonPrivateMethod(interfaceType.getDeclaredMethods());
        for (Class nextInterface : interfaceType.getInterfaces()) {
            recursiveAddInterfaceMethodsToList(nextInterface);
        }
    }

    private void collectMembers(Class type) {
    	parentClasses.add(type);
        if (type.isInterface()) {
            recursiveAddInterfaceMethodsToList(type);
            return;
        }
        boolean search = true;
        for (Constructor constructor : type.getDeclaredConstructors()) {
            if (Modifier.isPrivate(constructor.getModifiers())) continue;
            int length = constructor.getParameterTypes().length;
            if (search) {
                switch (length) {
                    case 0:
                        constructors.add(0, Method.getMethod(constructor));
                        search = false;
                        break;
                    case 1:
                        constructors.add(0, Method.getMethod(constructor));
                        break;
                    default:
                        constructors.add(Method.getMethod(constructor));
                        break;
                }
            }
        }
        Class nextClass = type;
        while (nextClass != Object.class) {
            addNonPrivateField(nextClass.getDeclaredFields());
            addNonPrivateMethod(nextClass.getDeclaredMethods());
            for (Class nextInterface : nextClass.getInterfaces())
            	recursiveAddInterfaceMethodsToList(nextInterface);
            nextClass = nextClass.getSuperclass();
        }
    }
	

	public void addField(String field, Class fieldClass) {
		fields.put(field, fieldClass);
	}

	public void addStaticField(String field, Class fieldClass) {
		staticFields.put(field, fieldClass);
	}

	public void addMethod(Method method) {
		methods.add(method);
	}

	public void addStaticMethod(Method method) {
		staticMethods.add(method);
	}
	
	public Class getMainType() {
		return mainType;
	}
	
	public Set> getParentClasses() {
		return parentClasses;
	}
	
	public List getConstructors() {
		return constructors;
	}
	
	public Map> getFields() {
		return fields;
	}
	
	public Map> getStaticFields() {
		return staticFields;
	}
	
	public Set getMethods() {
		return methods;
	}
	
	public Set getStaticMethods() {
		return staticMethods;
	}
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy