OK... so at least it sounds reasonable ;)     I attached a patch a the
r558780 level to TUSCANY-1206 to keep the discussion going.    It could
really use some careful review from you, Raymond, at least, and some rework
is needed to the newest code level, as this is pretty old.

There are some questions to answer..  a couple of these I already raised in
my note and at least one or two more (e.g. in the interface-wsdl
introspection is it OK to ignore the fault physical like I did?).

We can discuss in something like IRC if that's easier.

Thanks,
Scott






On 10/19/07, Raymond Feng <[EMAIL PROTECTED]> wrote:
>
> Hi, Scott.
>
> Sorry for the long .... delay. Your proposal sounds reasonable to me.
> Would
> you consider helping us by providing a patch?
>
> Thanks,
> Raymond
>
> ----- Original Message -----
> From: "Scott Kurz" <[EMAIL PROTECTED]>
> To: <[email protected]>
> Sent: Wednesday, October 10, 2007 8:20 AM
> Subject: Re: handling exceptions and faults better with the Tuscany
> databinding framework
>
>
> >I posted this and it probably got lost in the midst of  releasing 1.0 ...
> > let me resend now.
> >
> > Thanks,
> > Scott
> >
> >
> > On 9/15/07, Scott Kurz <[EMAIL PROTECTED]> wrote:
> >>
> >> In doing some work trying to leverage the Tuscany databinding framework
> >> to
> >> transform business exceptions across a binding, I noticed a couple
> issues
> >> relating to the need to handle both exception and fault DataType(s) .
> >>
> >> Basically, I'd like to discuss:
> >>
> >> * getting rid of the exception DataType and replacing it with simply a
> >> fault DataType.
> >> * decoupling the fault databinding from the way that the exception maps
> >> to
> >> a fault.
> >>
> >> Let me explain:
> >>
> >> Today, for Java interfaces, we build exception DataTypes during
> >> theintrospection phase
> >> and we set a databinding upon it.  This DB identifies an
> exceptionHandler
> >> which can (via getFaultType())  construct a fault DataType from the exc
> >> DataType.
> >>
> >> Different exception patterns result in different mappings between
> >> exception and fault data types.   For example, we have the pattern
> >> defined
> >> by JAX-WS Sec 2.5 in which the Java exception class wrappers a "fault
> >> bean" returned by the exception's getFaultInfo().   I'm thinking we
> also
> >> want to support POJO exceptions as well in certain contexts.
> >>
> >> Today we would support the JAX-WS Sec. 2.5 pattern by constructing an
> >> DataType wrappering the exception, introspecting the exception to find
> >> thefault
> >> and its databinding.   This databinding's exception handler would, at
> >> transform time, be used to construct a fault DataType representing
> >> thefault bean, distinct from
> >> the exception DataType.     This more or less works the same for JAXB
> >> andSDO, except that for SDO we have
> >> the Tuscany-ism of looking at FAULT_ELEMENT instead of @WebFault (
> which
> >> I
> >> mention below I'd like to change).
> >>
> >> For the POJO exception pattern, on the other hand, the fault DataType
> >> andexception DataType collapse into one as we see in
> >> the logic of JavaBeansExceptionHandler.
> >>
> >> I don't think we need the complexity of the two DataTypes;  I think all
> >> we
> >> really need from the exception DataType is its "physical', i.e. the
> Java
> >> Class of the exception type.   We use this to match the exception we
> have
> >> in-hand from the Java runtime with the DataType on the operation.   It
> is
> >> only the fault that gets transformed by the Tuscany databinding
> >> framework.
> >>
> >>
> >> Perhaps what would be better, instead of an exception DataType and
> fault
> >> DataType, would be to simply have the fault DataType with an additional
> >> "exceptionPhysical" member.    (We still need ExceptionHandler
> >> withgetFaultInfo()
> >> and createFaultException() as well).
> >>
> >> This would let us get the exception handlers out of the introspection
> >> business.
> >>
> >> If we look at DataBindingJavaInterfaceProcessor.processInterface()
> today,
> >> and see how the various databindings' exception handlers'
> getFaultType()s
> >> are called in order to find the right databinding to set on the
> exception
> >> DataType, it does seem messy to have to rely on this same
> getFaultType()
> >> method to work in a certain way and introspection time and transform
> >> time.
> >>
> >> The best reason, I think is elegance:  if it is the actual fault
> DataType
> >> which is interesting at transform time, and if we have an introspect
> >> step,
> >> let's have the introspect step set up this interesting fault
> >> DataType.      As an example, in  working on some binding impl code in
> >> thepast, I found myself calling this same getFaultType() method to get
> >> the fault from the exc...   making for at least three times this same
> >> getFaultType() method was called (Java introspect, my binding
> >> construction,
> >> and transform time).
> >>
> >> Then there is also performance to consider...
> >>
> >> ---------
> >>
> >> In addition, (and to some degree this is a separate point),  I think we
> >> should recognize certain patterns in which a Java exception relates to
> >> both
> >> the Java type of the "fault bean" and to a logical type and decouple
> >> these
> >> patterns from association with one of the various databinding impls we
> >> support.
> >>
> >> So, as an example, if you take the pattern in JAX-WS Sec. 2.5, you can
> >> have an exception with @WebFault(<fault elem>)  with a getFaultInfo()
> >> method returning a fault bean of any of the simple, SDO, or JAXB
> >> databindings.     I don't see the rationale for using FAULT_ELEMENT to
> >> denote the logical type when the fault bean is an SDO vs. using
> >> [EMAIL PROTECTED] for a JAXB;  I think this pattern should be decoupled 
> >> from
> >> the choice of databinding, and we don't want the same  algorithm
> (looking
> >> for @WebFault and using reflection to find the type returned by
> >> getFaultInfo(), etc.) to be re-coded for each databinding.
> >>
> >> (Though I don't think Tuscany has it presently, I coded a Simple DB
> >> ExceptionHandler which is largely just a copy of the
> SDOExceptionHandler,
> >> wihch illustrates my point.   Someone please correct me if Tuscany can
> >> already handle simple-typed fault beans in the JAX-WS Sec 2.5 pattern).
> >>
> >>
> >> In addition we'd have other patterns like POJO exception and maybe
> >> theAxis2 exception which Simon Nash recently did some work regarding.
> >>
> >>
> >> At this point I'd like to show some sample code, which is part of some
> >> changes I've run with successfully (some of my own tests in my own
> >> sandbox
> >> - not Tuscany tests yet).
> >>
> >>
> >>     public DataType<?> getFaultFromExceptionDataType(DataType<?>
> >> excDataType) {
> >>
> >>         //
> >>         // 1. Find the Java type of the fault bean, construct fault DT
> >> andset exc physical
> >>         //
> >>         Object excPhysical = excDataType.getPhysical();
> >>         if (!(excPhysical instanceof Class)) {
> >>             return null;    // Should we be throwing exc instead?
> >>         }
> >>         Class excClass = (Class)excPhysical;
> >>         Class faultBeanClass = null;
> >>         try {
> >>             Method method = excClass.getMethod("getFaultInfo",
> >> EMPTY_CLASS_ARRAY);
> >>             faultBeanClass = method.getReturnType();
> >>         } catch (NoSuchMethodException e) {
> >>             faultBeanClass = null;
> >>         }
> >>         if (faultBeanClass == null) {
> >>             return null;
> >>         }
> >>
> >>         // Only the physical is set here.
> >>         DataType faultDataType = new DataTypeImpl(null, faultBeanClass,
> >> null);
> >>         faultDataType.setExceptionPhysical(excClass);
> >>
> >>         //
> >>         // 2. Send through already-existing introspection routine
> >>         //
> >>
> >>         // Don't try to propagate annotations yet.  Note the DB on
> >> thefaultDataType
> >>         // is set by the databinding according to the implied contract
> we
> >> have going.
> >>         dataBindingRegistry.introspectType(faultDataType, null);
> >>
> >>         //
> >>         // 3) instantiate an exception handler for this fault from
> >> theappropriate DB
> >> and
> >>         //    set in the fault DT
> >>         //
> >>
> >>         DataBinding faultDataBinding =
> >> dataBindingRegistry.getDataBinding(
> >> faultDataType.getDataBinding());
> >>         ExceptionHandler excHandler =
> >> faultDataBinding.getExceptionHandler();
> >>         faultDataType.setExceptionHandler(excHandler);
> >>
> >>         //
> >>         // 4) set the logical from the @WebFault (FAULT_ELEMENT for
> now)
> >>         //
> >>         QName faultElement = null;
> >>         try {
> >>             Field field = excClass.getField("FAULT_ELEMENT");
> >>             faultElement = (QName)field.get(null);
> >>         } catch (NoSuchFieldException e) {
> >>             // Ignore
> >>         } catch (Throwable e) {
> >>             // Ignore
> >>         }
> >>         if (faultElement == null) {
> >>             // Should we be responsible for calculating a default
> >> fault_elem
> >>             // or leave this to someone else???
> >>             return null;
> >>         }
> >>
> >>         // Having set the physical and DB already, we now set the
> logical
> >> of the fault
> >>         faultDataType.setLogical(new XMLType(faultElement, null));
> >>
> >>         return faultDataType;
> >>
> >>     }
> >>
> >>
> >> The above is code that would be called in some form from
> >> DataBindingJavaInterfaceProcessor.processInterface(), passing in the
> >> exception DataType.
> >>
> >> In this code, I'm finding the fault bean class through a
> >> databinding-neutral
> >> look at the getFaultInfo() return type.  I'm then setting the DB on
> this
> >> based on the normal DB.introspect() routine (i.e. the same
> introspection
> >> of input and output types to find the databinding).
> >> Step 4 is to set the logical, again in a databinding-neutral way.
> >>
> >> I also have a step 3 where the ExceptionHandler is now stored in
> >> theDataType.   This is a non-trivial change which could probably
> >> really use some improvement (it brings up build and intra-project
> >> dependency issues).     I wanted to have a working prototype before
> >> posting this, however, and this is how I did it.    The
> ExceptionHandler
> >> still has the job of implementing createException() and getFaultInfo()
> >> but
> >>
> >> not getFaultType() any more
> >>
> >> I also have a simple routine to do something similar for "POJO
> >> exceptions"
> >> which do not have a fault bean and which have a Java, not an XML
> >> logical type.
> >>
> >>     public DataType<?> getFaultFromExceptionDataType(DataType<?>
> >> excDataType) {
> >>
> >>         //
> >>         // 1. Fault physical and Exception physical are one and the
> same
> >>         //
> >>         Object excPhysical = excDataType.getPhysical();
> >>         if (!(excPhysical instanceof Class)) {
> >>             return null;    // Should we be throwing exc instead?
> >>         }
> >>         Class excClass = (Class)excPhysical;
> >>
> >>         // Only the physical is set here.
> >>         DataType faultDataType = new DataTypeImpl(null, excClass,
> null);
> >>         faultDataType.setExceptionPhysical(excClass);
> >>
> >>         //
> >>         // 2. Send through already-existing introspection routine
> >>         //
> >>
> >>         // Don't try to propagate annotations yet.  Note the DB on
> >> thefaultDataType
> >>         // is set by the databinding according to the implied contract
> we
> >> have going.
> >>         dataBindingRegistry.introspectType(faultDataType, null);
> >>
> >>         //
> >>         // 3) instantiate an exception handler for this fault from
> >> theappropriate DB
> >> and
> >>         //    set in the fault DT
> >>         //
> >>
> >>         DataBinding faultDataBinding =
> >> dataBindingRegistry.getDataBinding(
> >> faultDataType.getDataBinding());
> >>         ExceptionHandler excHandler =
> >> faultDataBinding.getExceptionHandler();
> >>         faultDataType.setExceptionHandler(excHandler);
> >>
> >>         //
> >>         // 4) set the logical to be the exc class as well
> >>         //
> >>
> >>         // Having set the physical and DB already, we now set the
> logical
> >> of the fault
> >>         faultDataType.setLogical(excClass);
> >>
> >>         return faultDataType;
> >>
> >>     }
> >>
> >> Assuming it gets that far, I'm not sure whether it would be better to
> >> have
> >> these pieces of code in classes which are added to some registry
> >> (like the databinding registry), or whether it would be better to have
> >> one, master, order in which the exception to fault
> >> mapping is assumed to take place in Tuscany.
> >>
> >> I coded up a parallel modification in WSDL introspection in the class:
> >> org.apache.tuscany.sca.interfacedef.wsdl.introspect.WSDLOperation.
> >> Basically I just need to set "FaultException" as the exceptionPhysical
> on
> >> top of what had been done, as the "logical" was being set just fine
> >> already.
> >>
> >>
> >>
> ------------------------------------------------------------------------------
> >>
> >> So, this is getting long........
> >>
> >> Where I see this going from here is.. if this sounds interesting to
> >> people, it would be interesting to try incorporating
> >> the Axis2 exc->fault mapping pattern with the example from the recent
> >> JIRA
> >> Simon worked on into this new view I'm working on.
> >>
> >> Another pattern I could imagine would be the one mentioned in JAX-WS
> Sec.
> >> 3.7 in cases in which the exceptions don't conform to the Sec 2.5
> >> pattern.
> >>
> >> And it might be that my point about "decoupling" is only partially
> >> right.   Maybe the POJO exception case will always be associated
> >> withJavaBeans DB
> >> and maybe the JAX-WS Sec 3.7 case will always be associated withJAXB.
> >>
> >> However, I wanted to get this posted before thinking through all those
> >> permutations.
> >>
> >> Thanks,
> >> Scott
> >>
> >>
> >>
> >>
> >>
> >>
> >
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: [EMAIL PROTECTED]
> For additional commands, e-mail: [EMAIL PROTECTED]
>
>

Reply via email to