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