Author: cbegin
Date: Sat Jan 23 21:31:01 2010
New Revision: 902494

URL: http://svn.apache.org/viewvc?rev=902494&view=rev
Log:
ibatis-655  Mapper interface inheriatance support.

Modified:
    
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperMethod.java
    
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperProxy.java
    
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/builder/annotation/MapperAnnotationBuilder.java

Modified: 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperMethod.java
URL: 
http://svn.apache.org/viewvc/ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperMethod.java?rev=902494&r1=902493&r2=902494&view=diff
==============================================================================
--- 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperMethod.java
 (original)
+++ 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperMethod.java
 Sat Jan 23 21:31:01 2010
@@ -22,6 +22,7 @@
   private SqlCommandType type;
   private String commandName;
 
+  private Class declaringInterface;
   private Method method;
 
   private boolean returnsList;
@@ -32,13 +33,14 @@
 
   private boolean hasNamedParameters;
 
-  public MapperMethod(Method method, SqlSession sqlSession) {
+  public MapperMethod(Class declaringInterface, Method method, SqlSession 
sqlSession) {
     paramNames = new ArrayList<String>();
     paramPositions = new ArrayList<Integer>();
     this.sqlSession = sqlSession;
     this.method = method;
     this.config = sqlSession.getConfiguration();
     this.hasNamedParameters = false;
+    this.declaringInterface = declaringInterface;
     setupFields();
     setupMethodSignature();
     setupCommandType();
@@ -100,7 +102,7 @@
   // Setup //
 
   private void setupFields() {
-    this.commandName = method.getDeclaringClass().getName() + "." + 
method.getName();
+    this.commandName = declaringInterface.getName() + "." + method.getName();
   }
 
   private void setupMethodSignature() {

Modified: 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperProxy.java
URL: 
http://svn.apache.org/viewvc/ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperProxy.java?rev=902494&r1=902493&r2=902494&view=diff
==============================================================================
--- 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperProxy.java
 (original)
+++ 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/binding/MapperProxy.java
 Sat Jan 23 21:31:01 2010
@@ -26,14 +26,15 @@
   private <T> MapperProxy(SqlSession sqlSession) {
     this.sqlSession = sqlSession;
   }
-  
+
   public Object invoke(Object proxy, Method method, Object[] args) throws 
Throwable {
     try {
       if (!OBJECT_METHODS.contains(method.getName())) {
-        final MapperMethod mapperMethod = new MapperMethod(method, sqlSession);
+        final Class declaringInterface = findDeclaringInterface(proxy, method);
+        final MapperMethod mapperMethod = new MapperMethod(declaringInterface, 
method, sqlSession);
         final Object result = mapperMethod.execute(args);
         if (result == null && method.getReturnType().isPrimitive()) {
-          throw new BindingException("Mapper method '"+ method.getName()+"' 
("+method.getDeclaringClass()+") attempted to return null from a method with a 
primitive return type ("+method.getReturnType()+").");
+          throw new BindingException("Mapper method '" + method.getName() + "' 
(" + method.getDeclaringClass() + ") attempted to return null from a method 
with a primitive return type (" + method.getReturnType() + ").");
         }
         return result;
       }
@@ -43,6 +44,28 @@
     return null;
   }
 
+  private Class findDeclaringInterface(Object proxy, Method method) {
+    Class declaringInterface = null;
+    for (Class iface : proxy.getClass().getInterfaces()) {
+      try {
+        Method m = iface.getMethod(method.getName(), 
method.getParameterTypes());
+        if (declaringInterface != null) {
+          throw new BindingException("Ambiguous method mapping.  Two mapper 
interfaces contain the identical method signature for " + method);
+        } else if (m != null) {
+          declaringInterface = iface;
+        }
+      } catch (Exception e) {
+        // Intentionally ignore.
+        // This is using exceptions for flow control,
+        // but it's definitely faster.
+      }
+    }
+    if (declaringInterface == null) {
+      throw new BindingException("Could not find interface with the given 
method " + method);
+    }
+    return declaringInterface;
+  }
+
   public static <T> T newMapperProxy(Class<T> mapperInterface, SqlSession 
sqlSession) {
     ClassLoader classLoader = mapperInterface.getClassLoader();
     Class[] interfaces = new Class[]{mapperInterface};

Modified: 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/builder/annotation/MapperAnnotationBuilder.java
URL: 
http://svn.apache.org/viewvc/ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/builder/annotation/MapperAnnotationBuilder.java?rev=902494&r1=902493&r2=902494&view=diff
==============================================================================
--- 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/builder/annotation/MapperAnnotationBuilder.java
 (original)
+++ 
ibatis/java/ibatis-3/trunk/ibatis-3-core/src/main/java/org/apache/ibatis/builder/annotation/MapperAnnotationBuilder.java
 Sat Jan 23 21:31:01 2010
@@ -170,7 +170,7 @@
     SqlSource sqlSource = getSqlSourceFromAnnotations(method);
     if (sqlSource != null) {
       Options options = method.getAnnotation(Options.class);
-      final String mappedStatementId = method.getDeclaringClass().getName() + 
"." + method.getName();
+      final String mappedStatementId = type.getName() + "." + method.getName();
       boolean flushCache = false;
       boolean useCache = true;
       Integer fetchSize = null;


Reply via email to