/* * Copyright 2013 Guidewire Software, Inc. */ package gw.internal.gosu.parser.java.classinfo; import gw.internal.gosu.parser.java.IJavaASTNode; import gw.internal.gosu.parser.java.JavaASTConstants; import gw.internal.gosu.parser.java.JavaParser; import gw.lang.parser.TypeVarToTypeMap; import gw.lang.reflect.IType; import gw.lang.reflect.TypeSystem; import gw.lang.reflect.java.IJavaClassType; import gw.lang.reflect.java.IJavaClassTypeVariable; import gw.lang.reflect.java.ITypeInfoResolver; import gw.lang.reflect.java.JavaTypes; import gw.lang.reflect.module.IModule; import java.util.ArrayList; import java.util.List; public class JavaSourceTypeVariable implements IJavaClassTypeVariable { public static final JavaSourceTypeVariable[] EMPTY = new JavaSourceTypeVariable[0]; private IJavaASTNode boundNode; private String _name; private IJavaClassType[] _bounds; private ITypeInfoResolver _owner; private JavaSourceTypeVariable(ITypeInfoResolver owner, IJavaASTNode typeParameterNode) { _owner = owner; _name = typeParameterNode.getChildOfType(JavaParser.IDENTIFIER).getText(); boundNode = typeParameterNode.getChildOfType(JavaASTConstants.typeBound); } public static IJavaClassTypeVariable create(ITypeInfoResolver owner, IJavaASTNode node) { if (isValid(node)) { return new JavaSourceTypeVariable(owner, node); } else { return new UnparseableSourceTypeVariable(owner); } } public static boolean isValid(IJavaASTNode typeParameterNode) { return typeParameterNode.getChildOfType(JavaParser.IDENTIFIER) != null; } @Override public IJavaClassType getConcreteType() { return getBounds()[0].getConcreteType(); } @Override public String getNamespace() { return null; } public IJavaClassType[] getBounds() { if (_bounds == null) { if (boundNode != null) { List<IJavaASTNode> typeNodes = boundNode.getChildrenOfTypes(JavaASTConstants.type); _bounds = new IJavaClassType[typeNodes.size()]; for (int i = 0; i < _bounds.length; i++) { _bounds[i] = JavaSourceType.createType(_owner, typeNodes.get(i)); } } else { _bounds = new IJavaClassType[]{JavaTypes.OBJECT().getBackingClassInfo()}; } } return _bounds; } public String getName() { return _name; } @Override public String getSimpleName() { return getName(); } @Override public IModule getModule() { return _owner.getModule(); } @Override public IType getActualType(TypeVarToTypeMap typeMap) { return typeMap.getByString(getName()); } @Override public IType getActualType(TypeVarToTypeMap typeMap, boolean bKeepTypeVars) { IType typeFromMap = typeMap.getByString(getName()); if (typeFromMap != null) { return typeFromMap; } else { return TypeSystem.getErrorType(getName()); } } public String toString() { return getName() + " in " + _owner.toString(); } }