When referencing id of another resultMap in association/collection, unessesery ResultMap is created and stored in configuration. For example:

  1. When using nested collection:
  <resultMap id="BlogResultMap" type="Blog">
    <constructor>
      <idArg column="blog_id" name="id"/>
      <arg column="blog_title" name="title"/>
    </constructor>
    <collection property="posts" ofType="Post">
      <constructor>
        <idArg column="post_id" name="id"/>
        <arg column="post_body" name="body"/>
      </constructor>
    </collection>
  </resultMap>

Two ResultMaps are added to configuration: - BlogResultMap based on provided id of resultMap - mapper_resultMap[BlogResultMap]_collection[posts] for nested unnamed resultMap This works as expected so far.

  1. When referencing collection by id (different approach to map same result):
 <resultMap id="BlogResultMap" type="Blog">
    <constructor>
      <idArg column="blog_id" name="id"/>
      <arg column="blog_title" name="title"/>
    </constructor>
    <collection property="posts" resultMap="PostResultMap"/>
  </resultMap>

  <resultMap id="PostResultMap" type="Post">
    <constructor>
      <idArg column="post_id" name="id"/>
      <arg column="post_body" name="body"/>
    </constructor>
  </resultMap>

Three ResultMaps are added to configuration: - BlogResultMap based on provided id of 1st resultMap - PostResultMap based on provided id of 2nd resultMap - mapper_resultMap[BlogResultMap]_collection[posts] this one should not be created as it is not needed and doesn't even contain any mapped columns

Fix implemented in https://github.com/mybatis/mybatis-3/compare/master...piotrponikowski:remove-orphan-result-maps?expand=1#diff-c066585c40ce9a447125a1ba15b3a5a2

Method processNestedResultMappings should be evaluated only when attribute resultMap is empty.

Comment From: harawata

This seems like a good optimization. Thank you, @piotrponikowski !

How about using function to achieve lazy evaluation? If we add a new method taking Supplier in XNode ...

public String getStringAttribute(String name, Supplier<String> defSupplier) {
  String value = attributes.getProperty(name);
  return value == null ? defSupplier.get() : value;
}

... we can pass lambda which is evaluated only when the value above is null.

String nestedResultMap = context.getStringAttribute("resultMap", () -> 
    processNestedResultMappings(context, Collections.emptyList(), resultType));

Comment From: piotrponikowski

I like idea of Supplier, hovewer throws declaration on processNestedResultMappings make it harder to use it with lambda expressions:

private String processNestedResultMappings(...)throws Exception

We could add new functional interface like the one below, however this apporach requires more code.

  @FunctionalInterface
  public interface ThrowingSupplier<T> {
    T get() throws Exception;
  }
public String getStringAttribute(String name, ThrowingSupplier<String> defSupplier) throws Exception {
  String value = attributes.getProperty(name);
  return value == null ? defSupplier.get() : value;
}

There is also option to use simply try catch, but it doesn't look clean to me:

    String nestedResultMap = context.getStringAttribute("resultMap", () ->
    {
      try {
        return processNestedResultMappings(context, Collections.emptyList(), resultType);
      } catch (Exception e) {
        throw new RuntimeException(e);
      }
    });

I am not sure if I am familiar with functional interfaces enought to solve this in cleaner way. What do you think?

Comment From: harawata

I forgot to mention the exception, sorry. It seems that processNestedResultMappings() does not throw any checked exception and I have just removed it from the method declarations, so it shouldn't be a problem anymore. Could you rebase the branch and force-push with the new changes? (I'm sorry for the trouble, but the change I made was not directly related to this PR and I wanted to make it clear)

Comment From: piotrponikowski

Looks like I made some mistakes during rebase - will fix it tomorrow.

Comment From: piotrponikowski

Fixed PR to contain only related commits, hope it is ok now.

Comment From: harawata

LGTM. Thank you for the quick update, @piotrponikowski ! The change should be included in the latest 3.5.4-SNAPSHOT.