class JavaDomUtils {

    public static String calculateTypeName(CompilationUnit compilationUnit, FullyQualifiedJavaType fqjt) {

        if (fqjt.isArray()) {
            // if array, then calculate the name of the base (non-array) type
            // then add the array indicators back in
            String fqn = fqjt.getFullyQualifiedName();
            String typeName = calculateTypeName(compilationUnit,
                    new FullyQualifiedJavaType(fqn.substring(0, fqn.indexOf('['))));
            return typeName + fqn.substring(fqn.indexOf('['));
        }

        if (!fqjt.getTypeArguments().isEmpty()) {
            return calculateParameterizedTypeName(compilationUnit, fqjt);
        }

        if (compilationUnit == null
                || typeDoesNotRequireImport(fqjt)
                || typeIsInSamePackage(compilationUnit, fqjt)
                || typeIsAlreadyImported(compilationUnit, fqjt)) {
            return fqjt.getShortName();
        } else {
            return fqjt.getFullyQualifiedName();
        }
    }

}

class JavaDomUtilsTest {

    @Test
    public void testGenericTypeWithWildCardAllImported() {

        Interface interfaze = new Interface(new FullyQualifiedJavaType("com.foo.UserMapper"));

        interfaze.addImportedType(new FullyQualifiedJavaType("java.util.Map"));
        interfaze.addImportedType(new FullyQualifiedJavaType("java.util.List"));
        interfaze.addImportedType(new FullyQualifiedJavaType("com.beeant.dto.User"));
        interfaze.addImportedType(new FullyQualifiedJavaType("java.math.BigDecimal"));

        FullyQualifiedJavaType fqjt = new FullyQualifiedJavaType("java.util.Map<java.math.BigDecimal, java.util.List<? extends com.beeant.dto.User>>");
        assertEquals("Map<BigDecimal, List<? extends User>>",
                JavaDomUtils.calculateTypeName(interfaze, fqjt));
    }

}