| 

.NET C# Java Javascript Exception

1
Hallo zusammen,

ich hab wieder einmal eine Altlast Applikation vor der Nase und bin gerade am Refactoring. Grundlegend ist es eine Axis 1 Applikation und in den Clients ist immer wieder das selbe. Da es ja gegen das DRY Prinzip verstößt arbeite ich gerade daran die Client Klassen zu zerlegen.
Dabei ist mir immer wieder folgender Codeabschnitt ein Dorn im Auge:

/**
* Ändern des Status eines Antrags anhand seiner ID und der Depotnummer.
*
* @param {@link Integer} - Antrags-ID
* @param {@link String} - neuer Status
* @param {@link String} - Depotnummer
* @param {@link User} - Aktuell angemeldeter User
* @return {@link Antrag} - Antrag
* @throws WebServiceException Fehler beim ausführen des WebService
*/
public Antrag setStatus(Integer id, String status, String depotnr, User user) throws WebServiceException {
try {
Call call = createCall(user,"setStatus"); //Refacored

// Typenmappings für den Call setzen
AntragServiceBeanMapping map = new AntragServiceBeanMapping(call);
map.setAntrag();
map.setPerson();
......

// Parameter setzen
call.addParameter("id", XMLType.XSD_INTEGER, ParameterMode.IN);
call.addParameter("status", XMLType.XSD_STRING, ParameterMode.IN);
call.addParameter("depotnr", XMLType.XSD_STRING, ParameterMode.IN);
call.addParameter("username", XMLType.XSD_STRING, ParameterMode.IN);

return (Antrag) call.invoke(
new Object[] {
id,
status,
depotnr,
user.getUsername()
}
);

} catch (RemoteException re) {
logger.error("Fehler beim Ausführen des WebService", re);
throw new WebServiceException("Fehler beim Ausführen des WebService", re);
} catch (MalformedURLException mue) {
logger.error("Ungültige URL zum Zugriff auf den Webservic Server", mue);
throw new WebServiceException("Ungültige URL zum Zugriff auf den Webservic Server", mue);
} catch (ServiceException se) {
logger.error("Fehler beim Zugriff auf den Webservice Server", se);
throw new WebServiceException("Fehler beim Zugriff auf den Webservice Server", se);
}
}


Der untere Teil, also das Exception Handling ist in jeder Client Methode 1:1 das gleiche.
Ich hab schon überlegt den Invoke in eine externe Klasse auszulagern oder die ganzen Catches zu entfernen und einfach den Fehler werfen zu lassen, aber man will ja wissen wobei er abgebrochen ist. Daher überlege ich gerade ob ich nur allgemein alle Exceptions Abfange und in einer Klasse auslagere zum prüfen was der genaue Grund war.

Sonst finde ich nichts dazu, überall wird nur als Best Practice empfohlen die Exceptions wie hier zu Catchen und zu verarbeiten, aber immer das selbe hinschreiben bei 50 Methoden ist wirklich nicht sinnvoll, und das Exception Handling in das Frontend zu den Aufrufen zu verlegen ist nicht weniger Arbeit sondern mehr. Dort soll nur eine Exception abgefangen und behandelt werden mit einem entsprechenden Cause.

Evtl hat jemand einen Codeschnippsel dafür.

Gruß Lordi
05.02.2014
Lord_Pinhead 778 1 8
1 Antwort
1
Verdammt, ich hab meine Frage eigentlich selbst beantwortet :-)

1) In der Methode createCall der Superklasse einfach das Exception Handling einbauen

/**
* Standardcall erstellen und zurückgeben.
*
* <pre>
* {@code
* setUser(user); // Wichtig da der User verwendet wird zum Anmelden ans Backend
* Call call = createCall("setStatus");
* }
* </pre>
*
* @param {@link String} - Operationsname - z.B. open, search, insert usw.
* @return {@link Call} - Call
* @throws ServiceException
* @throws MalformedURLException
*/
protected Call createCall(String operationName) throws WebServiceException {
try {
Service service = new Service();
Call call = (Call) service.createCall();

// Authentifizierung
call.setUsername(getUser().getUsername());
call.setPassword(getUser().getPassword());
call.setTargetEndpointAddress(new URL(serviceUrl));

// Operation Name setzen
call.setOperationName(operationName);

return call;
} catch (MalformedURLException mue) {
throw new WebServiceException(
"Ungültige URL zum Zugriff auf den Webservic Server", mue);
} catch (ServiceException se) {
throw new WebServiceException(
"Fehler beim Zugriff auf den Webservice Server", se);
}
}


2) Den Invoke wirklich auslagern, ebenfalls in die Superklasse
/**
* Führt einen invoke für einen bestimmten Call aus. Beim Aufruf muss gecastet werden was für
* einen Objekt Typ man möchte.<p>
* Beispiel:
*
* <pre>
* {@code
* return (Antrag) execCall(call, new Object[] {id, status, depotnr,user.getUsername()});
* }
* </pre>
*
* @param {@link Call } - Call
* @param {@link Object} - Object Array mit den Parametern
* @return {@link Object} - undefiniert - bei Aufruf Casten
* @throws WebServiceException
*/
protected <T> T execCall(Call call, Object[] parameter) throws WebServiceException {
try {
return (T) call.invoke(parameter);
} catch (RemoteException re) {
throw new WebServiceException("Fehler beim Ausführen des WebService", re);
}
}


3) Clientmethode anpassen
/**
* Ändern des Status eines Antrags anhand seiner ID und der Depotnummer.
*
* @param {@link Integer} - Antrags-ID
* @param {@link String} - neuer Status
* @param {@link String} - Depotnummer
* @param {@link User - Aktuell angemeldeter User
* @return {@link Antrag} - Antrag
* @throws WebServiceException Fehler beim ausführen des WebService
*/
public Antrag setStatus(Integer id, String status, String depotnr, User user) throws WebServiceException {
try {
setUser(user);
Call call = createCall("setStatus");

// Typenmappings für den Call setzen
AntragServiceBeanMapping map = new AntragServiceBeanMapping(call);
map.setAntrag();
....

// Parameter setzen
call.addParameter("id", XMLType.XSD_INTEGER, ParameterMode.IN);
....
return (Antrag) execCall(call, new Object[] {id, status, depotnr,user.getUsername()});

} catch (WebServiceException mue) {
logger.error(mue.getCause().toString());
throw mue;
}
}


Die Menge der Parameter ist zwar nicht gerade gering, aber das kann ich sicherlich noch verkürzen indem ich in der Superklasse noch ein paar Sachen hinzufüge. Aber grundlegen ist das mein aktueller Weg der wie ich finde doch recht sauber ist.

Evtl. hat ja jemand etwas gegen den undefinierten Typ in der execCall Methode, aber so bin ich nicht gebunden was da hinten rauskommt und kann es normal verarbeiten.

Zumindest hab ich einen "Grünen Balken" ;-)
05.02.2014
Lord_Pinhead 778 1 8

Stelle deine Java-Frage jetzt!