2010-11-17 9 views
3

Avant d'errer et de recréer la roue, est-ce que quelqu'un connaît un wrapper JPA qui retourne les exceptions non vérifiées que JPA jette dans les exceptions vérifiées?Enveloppe JPA pour convertir les exceptions non contrôlées en exceptions vérifiées?

ne cherchez pas un argument au sujet de pourquoi je ne voudrais pas que des exceptions vérifiées, je ne veux :-)

+0

Toujours, pourquoi voudriez-vous faire cela? S'il n'y a pas un tel emballage, peut-être qu'il y a une raison derrière cela? :-P –

+0

'cuase la plupart des gens ne sont pas aussi pointilleux que je suis au sujet des exceptions? :-) – TofuBeer

+0

Avez-vous fini par rouler les vôtres? Se soucier de partager? –

Répondre

1

Vous pouvez faire 99% de rouler vos propres utilisant le code ci-dessous. Il vous laissera deux erreurs de compilation dues aux membres d'une collection qui ont besoin d'être encapsulés, mais cela vous amène au-delà du point où il ne vaut plus la peine d'automatiser.

package so; 

import javax.persistence.*; 

import java.io.File; 
import java.io.FileWriter; 
import java.lang.reflect.*; 

public class CheckedPersistenceMaker { 
static final String PACKAGE = "stackoverflow.javax.persistence"; 

static final String PACKAGE_DIR = PACKAGE.replace('.', '/'); 

static Class<?>[] CLASSES = new Class<?>[] { Cache.class, 
     EntityManager.class, EntityManagerFactory.class, 
     EntityTransaction.class, Parameter.class, 
     PersistenceUnitUtil.class, PersistenceUtil.class, 
     Persistence.class, Query.class, Tuple.class, TupleElement.class, 
     TypedQuery.class }; 


private static String getName(Class<?> c) { 
    String name = c.getName(); 
    for(Class<?> p:CLASSES) { 
     if (p.equals(c)) 
      return PACKAGE + ".Checked" 
        + name.substring(name.lastIndexOf('.') + 1); 
    } 
    return c.getName(); 
} 


static void generateWrapper(Class<?> c) throws Exception { 
    String name = c.getName(); 
    TypeVariable<?>[] genType = c.getTypeParameters(); 
    String varNames = ""; 
    if (genType != null && genType.length != 0) { 
     StringBuilder b = new StringBuilder(); 
     b.append("<"); 
     for(int i = 0;i < genType.length;i++) { 
      if (i > 0) b.append(","); 
      b.append(genType[i].getName()); 
     } 
     b.append(">"); 
     varNames = b.toString(); 
    } 
    name = "Checked" + name.substring(name.lastIndexOf('.') + 1); 
    File javaFile = new File(PACKAGE_DIR + "/" + name + ".java"); 
    javaFile.getParentFile().mkdirs(); 
    FileWriter w = new FileWriter(javaFile); 
    w.write("package " + PACKAGE + ";\n"); 
    w.write("public class " + name + varNames + " {\n"); 
    w.write(" private final " + c.getName() + varNames 
      + " wrapped;\n\n "); 
    w.write(name + "(" + c.getName() + varNames 
      + " original) {\nwrapped=original;\n}\n\n"); 
    w.write(" public " + c.getName() + varNames 
      + " getOriginal() { return wrapped; }\n\n"); 
    Method[] ms = c.getDeclaredMethods(); 
    for(Method m:ms) { 
     if (!Modifier.isPublic(m.getModifiers())) continue; 
     w.write(" "); 
     String s = m.toGenericString(); 
     s = s.replace(" abstract ", " "); 
     s = s.replace(c.getName() + ".", ""); 

     String q = s.substring(0, s.indexOf('(')); 
     if (q.indexOf('<',10) != -1) q = q.substring(0, q.indexOf('<',10)); 
     boolean needsTranslate = false; 

     for(Class<?> cc:CLASSES) { 
      String ccn = cc.getName(); 
      if (q.indexOf(ccn) != -1) needsTranslate = true; 
      String ccc = ccn.replace(cc.getPackage().getName() + ".", 
        PACKAGE + ".Checked"); 
      s = s.replace(ccn, ccc); 
     } 

     int pc = 0; 
     int p = s.indexOf('('); 
     if (s.charAt(p + 1) != ')') { 
      StringBuilder b = new StringBuilder(s); 
      int g = 0; 
      char ch; 
      do { 
       ch = b.charAt(p); 
       switch (ch) { 
       case '<': { 
        g++; 
        break; 
       } 
       case '>': { 
        g--; 
        break; 
       } 
       case ',': 
       case ')': { 
        if (g == 0) { 
         String pa = " p" + pc; 
         b.insert(p, pa); 
         pc++; 
         p += pa.length(); 
        } 
        break; 
       } 
       } 
       p++; 
      } while(ch != ')'); 
      s = b.toString(); 
     } 

     w.write(s); 

     w.write(" throws CheckedPersistenceException"); 

     Class<?>[] excs = m.getExceptionTypes(); 
     for(Class<?> e:excs) { 
      w.write(", " + e.getName()); 
     } 
     w.write(" {\n  try {\n   "); 

     Class<?> ret = m.getReturnType(); 
     if (!ret.equals(Void.TYPE)) { 
      w.write("return "); 
      if (needsTranslate) { 
       String retName = ret.getName(); 
       retName = retName.replace(c.getPackage().getName() + ".", 
         PACKAGE + ".Checked"); 
       w.write("new " + retName + "("); 
      } 
     } 

     if (Modifier.isStatic(m.getModifiers())) { 
      w.write(c.getName() + "." + m.getName() + "("); 
     } else { 
      w.write("wrapped." + m.getName() + "("); 
     } 

     Class<?> paramTypes[] = m.getParameterTypes(); 
     for(int i = 0;i < pc;i++) { 
      if (i > 0) w.write(','); 

      boolean isChecked = false; 
      for(int j=0;j<CLASSES.length;j++) { 
       if(CLASSES[j].equals(paramTypes[i])) isChecked=true; 
      } 
      w.write("p" + i); 
      if(isChecked) w.write(".getOriginal()"); 
     } 
     w.write(')'); 

     if (needsTranslate) w.write(')'); 
     w.write(";\n  } catch (javax.persistence.PersistenceException e) { throw new CheckedPersistenceException(e); }\n }\n\n"); 
    } 
    w.write("}\n"); 
    w.close(); 
} 


public static void main(String[] args) throws Exception { 
    for(Class<?> c:CLASSES) { 
     generateWrapper(c); 
    } 
} 
} 
+0

Je vais y jeter un coup d'oeil, merci! – TofuBeer