Coverage Report - org.mule.transformer.AbstractMessageTransformer
 
Classes in this File Line Coverage Branch Coverage Complexity
AbstractMessageTransformer
0%
0/50
0%
0/38
0
 
 1  
 /*
 2  
  * $Id: AbstractMessageTransformer.java 19250 2010-08-30 16:53:14Z dirk.olmes $
 3  
  * -------------------------------------------------------------------------------------
 4  
  * Copyright (c) MuleSoft, Inc.  All rights reserved.  http://www.mulesoft.com
 5  
  *
 6  
  * The software in this package is published under the terms of the CPAL v1.0
 7  
  * license, a copy of which has been included with this distribution in the
 8  
  * LICENSE.txt file.
 9  
  */
 10  
 
 11  
 package org.mule.transformer;
 12  
 
 13  
 import org.mule.DefaultMuleMessage;
 14  
 import org.mule.api.MuleEvent;
 15  
 import org.mule.api.MuleMessage;
 16  
 import org.mule.api.transformer.DataType;
 17  
 import org.mule.api.transformer.MessageTransformer;
 18  
 import org.mule.api.transformer.TransformerException;
 19  
 import org.mule.api.transformer.TransformerMessagingException;
 20  
 import org.mule.config.i18n.CoreMessages;
 21  
 import org.mule.config.i18n.Message;
 22  
 import org.mule.transformer.types.DataTypeFactory;
 23  
 import org.mule.transport.NullPayload;
 24  
 import org.mule.util.ClassUtils;
 25  
 import org.mule.util.StringMessageUtils;
 26  
 
 27  
 /**
 28  
  * <code>AbstractMessageTransformer</code> is a transformer that has a reference
 29  
  * to the current message. This message can be used to obtain properties associated
 30  
  * with the current message which are useful to the transform. Note that when part of a
 31  
  * transform chain, the MuleMessage payload reflects the pre-transform message state,
 32  
  * unless there is no current event for this thread, then the message will be a new
 33  
  * DefaultMuleMessage with the src as its payload. Transformers should always work on the
 34  
  * src object not the message payload.
 35  
  *
 36  
  * @see org.mule.api.MuleMessage
 37  
  * @see org.mule.DefaultMuleMessage
 38  
  */
 39  
 
 40  0
 public abstract class AbstractMessageTransformer extends AbstractTransformer implements MessageTransformer
 41  
 {
 42  
     /**
 43  
      * @param dataType the type to check against
 44  
      * @param exactMatch if set to true, this method will look for an exact match to
 45  
      *            the data type, if false it will look for a compatible data type.
 46  
      * @return whether the data type is supported
 47  
      */
 48  
     @Override
 49  
     public boolean isSourceDataTypeSupported(DataType<?> dataType, boolean exactMatch)
 50  
     {
 51  
         //TODO RM* This is a bit of hack since we could just register MuleMessage as a supportedType, but this has some
 52  
         //funny behaviour in certain ObjectToXml transformers
 53  0
         return (super.isSourceDataTypeSupported(dataType, exactMatch) || MuleMessage.class.isAssignableFrom(dataType.getType()));
 54  
     }
 55  
 
 56  
     /**
 57  
      * Perform a non-message aware transform. This should never be called
 58  
      */
 59  
     @Override
 60  
     public final Object doTransform(Object src, String enc) throws TransformerException
 61  
     {
 62  0
         throw new UnsupportedOperationException();
 63  
     }
 64  
 
 65  
     /**
 66  
      * Transform the message with no event specified.
 67  
      */
 68  
     @Override
 69  
     public final Object transform(Object src, String enc) throws TransformerException
 70  
     {
 71  
         try
 72  
         {
 73  0
             return transform(src, enc, null);
 74  
         }
 75  0
         catch (TransformerMessagingException e)
 76  
         {
 77  
             // Try to avoid double-wrapping
 78  0
             Throwable cause = e.getCause();
 79  0
             if (cause instanceof TransformerException)
 80  
             {
 81  0
                 TransformerException te = (TransformerException) cause;
 82  0
                 if (te.getTransformer() == this)
 83  
                 {
 84  0
                     throw te;
 85  
                 }
 86  
             }
 87  0
             throw new TransformerException(e.getI18nMessage(), this, e);
 88  
         }
 89  
     }
 90  
 
 91  
     /**
 92  
      * transform the specified message
 93  
      * @param src the data to transform
 94  
      * @param event the event currently being processed
 95  
      * @return
 96  
      * @throws TransformerMessagingException
 97  
      */
 98  
     public Object transform(Object src, MuleEvent event) throws TransformerMessagingException
 99  
     {
 100  0
         return transform(src, getEncoding(src), event);
 101  
     }
 102  
 
 103  
     /**
 104  
      * transform the specified message
 105  
      * @param src the data to transform
 106  
      * @param enc
 107  
      * @param event the event currently being processed
 108  
      * @return
 109  
      * @throws TransformerMessagingException
 110  
      */
 111  
     public final Object transform(Object src, String enc, MuleEvent event) throws TransformerMessagingException
 112  
     {
 113  0
         DataType<?> sourceType = DataTypeFactory.create(src.getClass());
 114  0
         if (!isSourceDataTypeSupported(sourceType))
 115  
         {
 116  0
             if (isIgnoreBadInput())
 117  
             {
 118  0
                 logger.debug("Source type is incompatible with this transformer and property 'ignoreBadInput' is set to true, so the transformer chain will continue.");
 119  0
                 return src;
 120  
             }
 121  
             else
 122  
             {
 123  0
                 Message msg = CoreMessages.transformOnObjectUnsupportedTypeOfEndpoint(getName(),
 124  
                     src.getClass(), endpoint);
 125  
                 /// FIXME
 126  0
                 throw new TransformerMessagingException(msg, event, this);
 127  
             }
 128  
         }
 129  0
         if (logger.isDebugEnabled())
 130  
         {
 131  0
             logger.debug(String.format("Applying transformer %s (%s)", getName(), getClass().getName()));
 132  0
             logger.debug(String.format("Object before transform: %s", StringMessageUtils.toString(src)));
 133  
         }
 134  
 
 135  
         MuleMessage message;
 136  0
         if (src instanceof MuleMessage)
 137  
         {
 138  0
             message = (MuleMessage) src;
 139  
         }
 140  0
         else if (muleContext.getConfiguration().isAutoWrapMessageAwareTransform())
 141  
         {
 142  0
             message = new DefaultMuleMessage(src, muleContext);
 143  
         }
 144  
         else
 145  
         {
 146  0
             if (event == null)
 147  
             {
 148  0
                 throw new TransformerMessagingException(CoreMessages.noCurrentEventForTransformer(), event, this);
 149  
             }
 150  0
             message = event.getMessage();
 151  0
             if (!message.getPayload().equals(src))
 152  
             {
 153  0
                 throw new IllegalStateException("Transform payload does not match current event");
 154  
             }
 155  
         }
 156  
 
 157  
         Object result;
 158  
         try
 159  
         {
 160  0
             result = transformMessage(message, enc);
 161  
         }
 162  0
         catch (TransformerException e)
 163  
         {
 164  0
             throw new TransformerMessagingException(e.getI18nMessage(), event, this, e);
 165  0
         }
 166  
 
 167  0
         if (result == null)
 168  
         {
 169  0
             result = NullPayload.getInstance();
 170  
         }
 171  
 
 172  0
         if (logger.isDebugEnabled())
 173  
         {
 174  0
             logger.debug(String.format("Object after transform: %s", StringMessageUtils.toString(result)));
 175  
         }
 176  
 
 177  0
         result = checkReturnClass(result, event);
 178  0
         return result;
 179  
     }
 180  
 
 181  
     /**
 182  
      * Check if the return class is supported by this transformer
 183  
      * @param object
 184  
      * @param event
 185  
      * @return
 186  
      * @throws TransformerMessagingException
 187  
      */
 188  
     protected Object checkReturnClass(Object object, MuleEvent event) throws TransformerMessagingException
 189  
     {
 190  
 
 191  
         //Null is a valid return type
 192  0
         if(object==null || object instanceof NullPayload && isAllowNullReturn())
 193  
         {
 194  0
             return object;
 195  
         }
 196  
 
 197  0
         if (returnType != null)
 198  
         {
 199  0
             DataType<?> dt = DataTypeFactory.create(object.getClass());
 200  0
             if (!returnType.isCompatibleWith(dt))
 201  
             {
 202  0
                 throw new TransformerMessagingException(
 203  
                         CoreMessages.transformUnexpectedType(dt, returnType),
 204  
                         event, this);
 205  
             }
 206  
         }
 207  
 
 208  0
         if (logger.isDebugEnabled())
 209  
         {
 210  0
             logger.debug("The transformed object is of expected type. Type is: " +
 211  
                     ClassUtils.getSimpleName(object.getClass()));
 212  
         }
 213  
 
 214  0
         return object;
 215  
     }
 216  
 
 217  
     /**
 218  
      * Transform the message
 219  
      * @param message
 220  
      * @param outputEncoding
 221  
      * @return
 222  
      * @throws TransformerMessagingException
 223  
      */
 224  
     public abstract Object transformMessage(MuleMessage message, String outputEncoding) throws TransformerException;
 225  
 }