private Type create(boolean entity, Class<?> cl, AnnotationHelper annotationHelper, Annotation annotation, java.lang.reflect.Type genericType,
            List<?> key) {
        if (cl.isPrimitive()) {
            cl = PrimitiveUtils.wrap(cl);
        }
        Type value;
        Type[] tempParams = (Type[]) Array.newInstance(Type.class,
                ReflectionUtils.getTypeParameterCount(genericType));
        cache.put(key, new ClassType(cl, tempParams));
        Type[] parameters = getParameters(cl, genericType);

        if (cl.isArray()) {
            Type componentType = get(cl.getComponentType());
            if (cl.getComponentType().isPrimitive()) {
                componentType = Types.PRIMITIVES.get(componentType);
            }
            value = componentType.asArrayType();
        } else if (cl.isEnum()) {
            value = new ClassType(TypeCategory.ENUM, cl);
        } else if (Number.class.isAssignableFrom(cl) && Comparable.class.isAssignableFrom(cl)) {
            value = new ClassType(TypeCategory.NUMERIC, cl, parameters);
        } else if (entity) {
            value = createOther(cl, entity, annotationHelper, annotation, parameters);
        } else if (Map.class.isAssignableFrom(cl)) {
            value = new SimpleType(Types.MAP, parameters[0], asGeneric(parameters[1]));
        } else if (List.class.isAssignableFrom(cl)) {
            value = new SimpleType(Types.LIST, asGeneric(parameters[0]));
        } else if (Set.class.isAssignableFrom(cl)) {
            value = new SimpleType(Types.SET, asGeneric(parameters[0]));
        } else if (Collection.class.isAssignableFrom(cl)) {
            value = new SimpleType(Types.COLLECTION, asGeneric(parameters[0]));
        } else {
            value = createOther(cl, entity, annotationHelper, annotation, parameters);
        }

        if (genericType instanceof TypeVariable) {
            TypeVariable tv = (TypeVariable) genericType;
            if (tv.getBounds().length == 1 && tv.getBounds()[0].equals(Object.class)) {
                value = new TypeSuper(tv.getName(), value);
            } else {
                value = new TypeExtends(tv.getName(), value);
            }
        }

        if (entity && !(value instanceof EntityType)) {
            value = new EntityType(value, variableNameFunction);
        }
        return value;
    }
{@code TypeFactory} is a factory class for {@link Type} instances

@author tiwe
querydsl-codegen/src/main/java/com/querydsl/codegen/TypeFactory.java