Topic
  • 3 replies
  • Latest Post - ‏2015-01-16T18:15:30Z by vinceisvince
SystemAdmin
SystemAdmin
6772 Posts

Pinned topic Naming MTOM Attachments.

‏2013-02-08T04:06:04Z |
Hi, I have a question. Is it possible to specify a dynamic name while creating MTOM attachments from a base-64 field.
I have created an MTOM Policy, but am not sure how to pass in a variable into the Content ID field.

The only other option I see, is to try and rename and recreate the attachments after the MTOM XML and attachments have been created.
Can anyone help ??
(Either with the MTOM Policy OR the XSL to recreate the attachments based on another field in the XML)

Thanks,
Neelam.
Updated on 2013-02-11T15:53:16Z at 2013-02-11T15:53:16Z by SystemAdmin
  • HermannSW
    HermannSW
    4647 Posts

    Re: Naming MTOM Attachments.

    ‏2013-02-08T10:22:36Z  
    Hi Neelam,

    unfortunately "ContentID" is just a string, from "store:///xml-mgmt.xsd":
    
    ... <!--MTOM Rule--> <xsd:complexType name=
    "dmMtomRule"> <xsd:sequence> <xsd:element name=
    "XPath" type=
    "tns:dmXPathExpr" minOccurs=
    "1" maxOccurs=
    "1" /> <xsd:element name=
    "ContentType" type=
    "tns:dmString" nillable=
    "1" minOccurs=
    "1" maxOccurs=
    "1" /> <xsd:element name=
    "ContentID" type=
    "tns:dmString" nillable=
    "1" minOccurs=
    "1" maxOccurs=
    "1" /> </xsd:sequence> </xsd:complexType> ...
    


    Good news, although there is no "Content-ID rename" feature, below stylesheet does what you want.
    Attachment processing of binary attachments is described eg. on slide 18 of this webcast:
    http://www-01.ibm.com/support/docview.wss?uid=swg27022979
    The basics can be found in this webcast:
    http://www-01.ibm.com/support/docview.wss?uid=swg27022977

    This is the input document, containing base64 encoded sequence "0x74 0x65 0x00 0x74":
    
    $ cat te0t.b64.xml <x>dGUAdA==</x> $
    


    This is what the MTOM-encode produces without modification (the '0x00' does not get displayed, but its there):
    
    $ curl --data-binary @te0t.b64.xml http:
    //dp7-l3:2049 ; echo     --13da7d40-145e-47c5-9861-9f75ef9ff8fc Content-Type: application/xop+xml; type=
    "application/soap+xml" Content-Transfer-Encoding: binary   <?xml version=
    "1.0" encoding=
    "UTF-8"?> <x><xop:Include href=
    "cid:PLACEHOLDER1" xmlns:xop=
    "http://www.w3.org/2004/08/xop/include"/></x> --13da7d40-145e-47c5-9861-9f75ef9ff8fc Content-ID: <PLACEHOLDER1> Content-Transfer-Encoding: binary Content-Type: imgif   tet --13da7d40-145e-47c5-9861-9f75ef9ff8fc--   $
    


    As you can see after applying the stylesheet, Content-ID 'PLACEHOLDER1' has been replaced by 'new-cid'.
    Important is, that the <xop:Include> referencing the attachment gets updated, too!
    
    $ curl --data-binary @te0t.b64.xml http:
    //dp7-l3:2049 ; echo     --874508f0-0369-40ba-9c7b-257dd9bcee4f Content-Type: application/xop+xml; type=
    "application/soap+xml" Content-Transfer-Encoding: binary   <?xml version=
    "1.0" encoding=
    "UTF-8"?> <x><xop:Include xmlns:xop=
    "http://www.w3.org/2004/08/xop/include" href=
    "cid:new-cid"/></x> --874508f0-0369-40ba-9c7b-257dd9bcee4f Content-ID: <new-cid> Content-Transfer-Encoding: binary Content-Type: application/octet-stream   tet --874508f0-0369-40ba-9c7b-257dd9bcee4f--   $
    


    And here is the stylesheet, it just does
    • (binary) read of the attachment
    • attach it again with new Content-ID
    • remove the original attachment
    • identity transformation with adjustment of xop:Include/@href
    
    <!-- Howto rename attachment Content-ID   
    'xwa' is name of input context of transform action running 
    
    this stylesheet --> <xsl:stylesheet version=
    "1.0" xmlns:xsl=
    "http://www.w3.org/1999/XSL/Transform" xmlns:func=
    "http://exslt.org/functions" xmlns:dp=
    "http://www.datapower.com/extensions" extension-element-prefixes=
    "dp" exclude-result-prefixes=
    "func" > <!-- nice to have functions 
    
    for dealing with attachments --> <func:function name=
    "func:cid"> <xsl:param name=
    "name"/>  <func:result select=
    "concat('cid:',$name)"/> </func:function>   <func:function name=
    "func:att"> <xsl:param name=
    "ctx"/> <xsl:param name=
    "name"/>   <func:result select=
    "concat('attachment://',$ctx,'/',func:cid($name))"/> </func:function>   <xsl:template match=
    "/">   <!-- (binary) read attachment --> <xsl:variable name=
    "resp"> <dp:url-open target=
    "{func:att('xwa','PLACEHOLDER1')}" response=
    "binaryNode"/> </xsl:variable>   <!-- attach it again to context 
    "xwa", with 
    
    new Content-ID --> <dp:url-open target=
    "{func:att('xwa','new-cid')}" data-type=
    "base64" response=
    "ignore" content-type=
    "application/octet-stream" > <xsl:value-of select=
    "dp:binary-encode($resp/result/binary/node())" /> </dp:url-open> <!-- now remove original attachment --> <dp:strip-attachments uri=
    "{func:cid('PLACEHOLDER1')}" context=
    "xwa"/>   <!-- 
    
    finally 
    
    do identity xform and adjust 
    'xop:Include/@href' --> <xsl:apply-templates />   </xsl:template>     <xsl:template match=
    "@href[.='cid:PLACEHOLDER1' and name(..)='xop:Include']"> <xsl:attribute name=
    "href">cid:new-cid</xsl:attribute> </xsl:template>   <xsl:template match=
    "node()"> <xsl:copy> <xsl:apply-templates select=
    "@*"/> <xsl:apply-templates select=
    "node()"/> </xsl:copy> </xsl:template>   </xsl:stylesheet>
    


    Find attached the 4.0.2.9 export of the service I used for easy playing.

     
    Hermann<myXsltBlog/> <myXsltTweets/>

    Attachments

  • SystemAdmin
    SystemAdmin
    6772 Posts

    Re: Naming MTOM Attachments.

    ‏2013-02-11T15:53:16Z  
    Thanks so much Hermann !!!
    I would just liked to add that, for some reason, the attachments do not get renamed if the probe is ON.
    I spent quite some time on this on Friday, trying to figure out why it was not working. :)
    Turned the probe OFF and it worked ;)

    You rock !!!
  • vinceisvince
    vinceisvince
    2 Posts

    Re: Naming MTOM Attachments.

    ‏2015-01-16T18:15:30Z  
    • HermannSW
    • ‏2013-02-08T10:22:36Z
    Hi Neelam,

    unfortunately "ContentID" is just a string, from "store:///xml-mgmt.xsd":
    <pre class="jive-pre"> ... <!--MTOM Rule--> <xsd:complexType name= "dmMtomRule"> <xsd:sequence> <xsd:element name= "XPath" type= "tns:dmXPathExpr" minOccurs= "1" maxOccurs= "1" /> <xsd:element name= "ContentType" type= "tns:dmString" nillable= "1" minOccurs= "1" maxOccurs= "1" /> <xsd:element name= "ContentID" type= "tns:dmString" nillable= "1" minOccurs= "1" maxOccurs= "1" /> </xsd:sequence> </xsd:complexType> ... </pre>

    Good news, although there is no "Content-ID rename" feature, below stylesheet does what you want.
    Attachment processing of binary attachments is described eg. on slide 18 of this webcast:
    http://www-01.ibm.com/support/docview.wss?uid=swg27022979
    The basics can be found in this webcast:
    http://www-01.ibm.com/support/docview.wss?uid=swg27022977

    This is the input document, containing base64 encoded sequence "0x74 0x65 0x00 0x74":
    <pre class="jive-pre"> $ cat te0t.b64.xml <x>dGUAdA==</x> $ </pre>

    This is what the MTOM-encode produces without modification (the '0x00' does not get displayed, but its there):
    <pre class="jive-pre"> $ curl --data-binary @te0t.b64.xml http: //dp7-l3:2049 ; echo --13da7d40-145e-47c5-9861-9f75ef9ff8fc Content-Type: application/xop+xml; type= "application/soap+xml" Content-Transfer-Encoding: binary <?xml version= "1.0" encoding= "UTF-8"?> <x><xop:Include href= "cid:PLACEHOLDER1" xmlns:xop= "http://www.w3.org/2004/08/xop/include"/></x> --13da7d40-145e-47c5-9861-9f75ef9ff8fc Content-ID: <PLACEHOLDER1> Content-Transfer-Encoding: binary Content-Type: imgif tet --13da7d40-145e-47c5-9861-9f75ef9ff8fc-- $ </pre>

    As you can see after applying the stylesheet, Content-ID 'PLACEHOLDER1' has been replaced by 'new-cid'.
    Important is, that the <xop:Include> referencing the attachment gets updated, too!
    <pre class="jive-pre"> $ curl --data-binary @te0t.b64.xml http: //dp7-l3:2049 ; echo --874508f0-0369-40ba-9c7b-257dd9bcee4f Content-Type: application/xop+xml; type= "application/soap+xml" Content-Transfer-Encoding: binary <?xml version= "1.0" encoding= "UTF-8"?> <x><xop:Include xmlns:xop= "http://www.w3.org/2004/08/xop/include" href= "cid:new-cid"/></x> --874508f0-0369-40ba-9c7b-257dd9bcee4f Content-ID: <new-cid> Content-Transfer-Encoding: binary Content-Type: application/octet-stream tet --874508f0-0369-40ba-9c7b-257dd9bcee4f-- $ </pre>

    And here is the stylesheet, it just does
    • (binary) read of the attachment
    • attach it again with new Content-ID
    • remove the original attachment
    • identity transformation with adjustment of xop:Include/@href
    <pre class="jive-pre"> <!-- Howto rename attachment Content-ID 'xwa' is name of input context of transform action running this stylesheet --> <xsl:stylesheet version= "1.0" xmlns:xsl= "http://www.w3.org/1999/XSL/Transform" xmlns:func= "http://exslt.org/functions" xmlns:dp= "http://www.datapower.com/extensions" extension-element-prefixes= "dp" exclude-result-prefixes= "func" > <!-- nice to have functions for dealing with attachments --> <func:function name= "func:cid"> <xsl:param name= "name"/> <func:result select= "concat('cid:',$name)"/> </func:function> <func:function name= "func:att"> <xsl:param name= "ctx"/> <xsl:param name= "name"/> <func:result select= "concat('attachment://',$ctx,'/',func:cid($name))"/> </func:function> <xsl:template match= "/"> <!-- (binary) read attachment --> <xsl:variable name= "resp"> <dp:url-open target= "{func:att('xwa','PLACEHOLDER1')}" response= "binaryNode"/> </xsl:variable> <!-- attach it again to context "xwa", with new Content-ID --> <dp:url-open target= "{func:att('xwa','new-cid')}" data-type= "base64" response= "ignore" content-type= "application/octet-stream" > <xsl:value-of select= "dp:binary-encode($resp/result/binary/node())" /> </dp:url-open> <!-- now remove original attachment --> <dp:strip-attachments uri= "{func:cid('PLACEHOLDER1')}" context= "xwa"/> <!-- finally do identity xform and adjust 'xop:Include/@href' --> <xsl:apply-templates /> </xsl:template> <xsl:template match= "@href[.='cid:PLACEHOLDER1' and name(..)='xop:Include']"> <xsl:attribute name= "href">cid:new-cid</xsl:attribute> </xsl:template> <xsl:template match= "node()"> <xsl:copy> <xsl:apply-templates select= "@*"/> <xsl:apply-templates select= "node()"/> </xsl:copy> </xsl:template> </xsl:stylesheet> </pre>

    Find attached the 4.0.2.9 export of the service I used for easy playing.

     
    Hermann<myXsltBlog/> <myXsltTweets/>

    I've been using XSLT less than a year now and I have a question.

    I took pieces from your example to possibly simplify

    My problem is the MIMEType.  I have the mimeType available and I'm working with the response of an ecoded file.  Of course as the content type is only a string input in MTOM policy.

     

    This might be more of a question of understanding.  WOrking with attachments, I always have to do it in a request/response fashion.  If I base 64 a file from a url-open I can't immediately run an MTOM policy on it in XSLT.  For some reason I need to do MTOM policy on the response.  Likewise I can't seem to create a file in the response XSLT.  I'd like to do much more in XSLT rather than going through transforms and editing policy rules.

     

    I tried something like this 

                    <!-- Create new file with correct MIMEType --> (resulted in error opening URL)

     

                    <xsl:call-template name="mtom-implementation"> <!--Creates '123456789' attachment-->
                        <xsl:with-param name="policyname" select="'MTOM'"/>
                    </xsl:call-template>

     

                    <!-- can't create a new file...? This fails-->
                    <dp:url-open target="attachment://cid:123456" data-type="base64" response="ignore" content-type="{./MIMEType}">
                        <xsl:value-of select="./attachmentReference" />
                    </dp:url-open>
                                    

                    
                        
                    <!-- Remove older file which I can do-->
                    <dp:strip-attachments uri="cid:123456789"/>

     

    I will try what was said in your documentation as I think I can make it work but seems like a lot of work just to change MIMEType/contentId

     

    *UPDATE*

    I have this working using your method.  My attachment is being added only when PROBE is on, of course I need it to work when the PROBE is off.   I created a echo firewall to handle attachments which are inline base64 under "attachmentReference".  When probe is off I get no attachment.  THe xop:include is changed to the filename and all that but there's no attachment in the message..  Here is my code:

     

    <xsl:stylesheet version="1.0"
        xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:func="http://exslt.org/functions"
            xmlns:dp="http://www.datapower.com/extensions" xmlns:xop="http://www.w3.org/2004/08/xop/include"
            extension-element-prefixes="dp" exclude-result-prefixes="func">
    
            <xsl:template match="/">
    
                    <!-- (binary) read attachment -->
                    <xsl:variable name="resp">
                            <dp:url-open target="{//xop:Include/@href}" response="binaryNode" />
                    </xsl:variable>
    
                    <xsl:variable name="cid">
                            <xsl:choose>
                                    <xsl:when test="string-length(//filename) &gt; 0">
                                            <xsl:value-of select="concat('cid:',//filename)" />
                                    </xsl:when>
                                    <xsl:otherwise>
                                            <xsl:text>cid:newCID</xsl:text>
                                    </xsl:otherwise>
                            </xsl:choose>
                    </xsl:variable>
    
                    <dp:url-open target="{$cid}" data-type="base64" response="ignore"
                            content-type="{//MIMEType}">
                            <xsl:value-of select="dp:binary-encode($resp/result/binary/node())" />
                    </dp:url-open>
    
                    <!-- now remove original attachment -->
                    <dp:strip-attachments uri="{//xop:Include/@href}" />
    
                    
                    <xsl:apply-templates/>
            </xsl:template>
    
            
            <xsl:template match="@href[name(..)='xop:Include']">
    
                    <xsl:attribute name="href">
                            <xsl:value-of select="concat('cid:',../../../filename)" />
                    </xsl:attribute>
                    
            </xsl:template>
    
            <xsl:template match="node()">
                    <xsl:copy>
                            <xsl:apply-templates select="@*" />
                            <xsl:apply-templates select="node()" />
                    </xsl:copy>
            </xsl:template>
    
    
    
    </xsl:stylesheet>
    

     

    Updated on 2015-01-21T20:00:12Z at 2015-01-21T20:00:12Z by vinceisvince