cancel
Showing results for 
Search instead for 
Did you mean: 

Setting dynamic attachment name in mail adapter

Former Member
0 Kudos

Hi experts,

I have a mail adapter that send e-mails from ECC to several address.

I have configured dynamically the FROM and TO field using the code showed below in message mapping:

public String SetMailParameters(String Mail_address_to, Container container){

//write your code here

String valueFrom = "my_address";

DynamicConfiguration conf = (DynamicConfiguration) container.getTransformationParameters().get(StreamTransformationConstants.DYNAMIC_CONFIGURATION);

DynamicConfigurationKey key1 = DynamicConfigurationKey.create( "http://sap.com/xi/XI/System/Mail", "THeaderFROM");

DynamicConfigurationKey key2 = DynamicConfigurationKey.create( "http://sap.com/xi/XI/System/Mail", "THeaderTO");

conf.put(key1, valueFrom);

conf.put(key2, Mail_address_to);

return "";

In communication channel I have checked ASMA and variable transport binding (using XHeaderName1 and 2), mail package is not checked.

It works fine!

My question is:

I need to dynamically configure also the Attachment name: is it possible?

I've tried adding the code below:

DynamicConfigurationKey key3 = DynamicConfigurationKey.create("http://sap.com/xi/XI/System/File","FileName");

conf.put(key3,Attachment_name);

and also

Transform.ContentDisposition attachment;filename=<FileName>

in Message TransformBean in communication channel, but it doesn't work!!!

Any idea?

Thanks

Fabio Boni

Accepted Solutions (1)

Accepted Solutions (1)

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

Yes,this is possible using option 'Use Mail Package' and then poulating fields in standard Mail.xsd.

Attachment name can be set by mapping "attachment; filename="{desired name or field in structure}" to Content-Disposition field in Mail.xsd.

Please let me know if you need more details.

Thanks.

Regards,

Shweta

Former Member
0 Kudos

Hi,

thanks for reply.

Now I'm not using mail package and it works for FROM and TO fields. Is not possible to do this without using mail package?

Fabio

Former Member
0 Kudos

If I use mail package, how I have to use it?

I have imported it in integration builder as an external definiton, but now I don't know how to proceed.

I already have my message mapping with source and target structure, how I implement mail package? In target structure?

Thanks

Fabio

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

For this,you have to create an additional mapping from your target structure to Mail Structure where you can use your DynamicConfiguration UDF to set FROM and TO fields and for Content-Disposition,you can set desired attachment name or if you want it from your payload.

Content field has to contain your entire payload.You can write a UDF to do this.

If required,I can provide you the code for this UDF.But before this,would it be possible to see your target structure?

Based on this,we need to create our UDF.

Thanks.

Regards,

Shweta

Former Member
0 Kudos

Hi, thanks for help!!

I've implemented mail.xsd in target structure, so now in message mapping I have 1 source structure and 2 target structures (one is the mail package).

I think is correct, tell me if I'm wrong.

My requirement is to dynamically fulfil the to field and the name of attachment.

For the to field I've linked the to field of mail package with a source field containing address coming from ECC side.

For attachment name I don't know!!!

This is my target structure:

<?xml version="1.0" encoding="UTF-8"?>

<ns0:Messages xmlns:ns0="http://sap.com/xi/XI/SplitAndMerge">

<ns0:Message1>

<ns2:Mailxmlns:ns2="http://sap.com/xi/XI/Mail/30">

<To>address</To>

<Content>attachmentname</Content>

</ns2:Mail>

</ns0:Message1>

<ns0:Message2>

<ns1:MT_DailyShipped_XXXX xmlns:ns1="urn:AAAXXX:DailyShipped">

<DetailRecord>

<Delivery_type>r</Delivery_type>

<Sold_to></Sold_to>

<Sold_to_description>f</Sold_to_description>

<Issue_slip_number></Issue_slip_number><Goods_movement_date></Goods_movement_date><Delivery_item></Delivery_item><Shipping_condition></Shipping_condition><Incoterms></Incoterms><Material_number></Material_number><Material_description></Material_description><Delivery_quantity></Delivery_quantity><Currency></Currency><Gross_price></Gross_price><Total_discounts></Total_discounts><Total_rises></Total_rises><Net_price></Net_price><Sales_document_date></Sales_document_date><Sales_document_number></Sales_document_number><Document_item></Document_item><PO_number></PO_number><PO_date></PO_date><Order_quantity></Order_quantity><Invoice_number></Invoice_number><Invoice_date></Invoice_date><Invoice_item></Invoice_item><Invoice_quantity></Invoice_quantity></DetailRecord></ns1:MT_DailyShipped_XXX>

</ns0:Message2>

</ns0:Messages>

Fabio Boni

Former Member
0 Kudos

Hi, thanks for help!!

I've implemented mail.xsd in target structure, so now in message mapping I have 1 source structure and 2 target structures (one is the mail package).

I think is correct, tell me if I'm wrong.

My requirement is to dynamically fulfil the to field and the name of attachment.

For the to field I've linked the to field of mail package with a source field containing address coming from ECC side.

For attachment name I don't know!!!

This is my target structure:

<?xml version="1.0" encoding="UTF-8"?>

<ns0:Messages xmlns:ns0="http://sap.com/xi/XI/SplitAndMerge">

<ns0:Message1>

<ns2:Mailxmlns:ns2="http://sap.com/xi/XI/Mail/30">

<To>address</To>

<Content>attachmentname</Content>

</ns2:Mail>

</ns0:Message1>

<ns0:Message2>

<ns1:MT_DailyShipped_XXXX xmlns:ns1="urn:AAAXXX:DailyShipped">

<DetailRecord>

<Delivery_type>r</Delivery_type>

<Sold_to></Sold_to>

<Sold_to_description>f</Sold_to_description>

<Issue_slip_number></Issue_slip_number><Goods_movement_date></Goods_movement_date><Delivery_item></Delivery_item><Shipping_condition></Shipping_condition><Incoterms></Incoterms><Material_number></Material_number><Material_description></Material_description><Delivery_quantity></Delivery_quantity><Currency></Currency><Gross_price></Gross_price><Total_discounts></Total_discounts><Total_rises></Total_rises><Net_price></Net_price><Sales_document_date></Sales_document_date><Sales_document_number></Sales_document_number><Document_item></Document_item><PO_number></PO_number><PO_date></PO_date><Order_quantity></Order_quantity><Invoice_number></Invoice_number><Invoice_date></Invoice_date><Invoice_item></Invoice_item><Invoice_quantity></Invoice_quantity></DetailRecord></ns1:MT_DailyShipped_XXX>

</ns0:Message2>

</ns0:Messages>

Fabio Boni

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

I am sorry,if I have not explained it correctly but you don't need to have multimapping in this case.

Looking at your target structure,I see that you have only one level(fields under DetailRecord),so if we leave apart Mail.xsd additions,your original scenario would have been a simple mapping between your source and target structure without Multimapping(Message1,Message2 ,etc),is this correct?

Please keep this mapping as it is without changes.

Now,create a new mapping taking source as your target structure and target as Mail.xsd.Both these mappings should have one source and one target each.

Map your UDF to populate FROM and TO fields.

Create some UDFs as:

1) Concat Value

public String concatValue(String Delivery_type,String Sold_to,{all your fields}........,Container container){

String str=null;

str=Delivery_type";"Sold_to";"....... //For creating semicolon separated file,please change it your format

return str;

2) Create Content- Pass output of concatValue to this UDF

public void createContent(String[] a,ResultList result,Container container){

AbstractTrace trace = container.getTrace();

String str = "";

for(int i=0;i<a.length;i++)

{

if(i == (a.length-1))

str = str + a<i>;

else

str = str + a<i> + "\n";

}

result.addValue(str);

In str = str + a : a is an array with index i ,index goes off when I post it

3)Map output of Create Content to Content field in Mail.xsd.

Please let me know if this works.

Thanks.

Regards,

Shweta

Former Member
0 Kudos

<Hello Fabio,

For this,you have to create an additional mapping from your target structure to Mail Structure where you can use your DynamicConfiguration UDF to set FROM and TO fields and for Content-Disposition,you can set desired attachment name or if you want it from your payload.>

Sorry, maybe I didn't understand this point.

I have to change Interface Mapping like this:

1 source interface --> 1 target interface

1 target interface (the same as above) --> mail package

?

Now Im is:

1 source interface --> 1 target interface.

If so, what I've to do im Message Mapping?

thanks

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

When you follow these steps,you have two Message mappings:

1) Your original one

2) Your target to Mail.xsd.

You need to change IM as:

1) Source - Keep Source Interface as it is (this is the source interface of your first mapping)

2) Target Interface : Message Interface created with Mail.xsd

Under Mapping Program,you will have two mappings (first,your original,then this mail mapping)

Is this fine now?

Regards,

Shweta

Former Member
0 Kudos

Hi,

I have done the changes suggested in Integration Repository.

Now in Integration Directory what I have to do?

Now I use module message transform bean with the field of the old target interface mapped

I have to change receiver agreement, receiver determination,...?

Thanks

Fabio

Edited by: Fabio Boni on Sep 2, 2010 12:45 PM

shweta_walaskar2
Contributor
0 Kudos

Hi Fabio,

You don't need to change receiver agreement, receiver determination,etc

Only your Mail receiver communication will change.

Check options 'Use Mail Package' and 'Keep Attachments'

Can you please let me know your message transform bean configuration so that we can check if this has to be changed?

Thanks.

Regards,

Shweta

Former Member
0 Kudos

Hi,

I have

1 localejbs/AF_Modules/MessageTransformBean Local Enterprise Bean mailAttachment

2 sap.com/com.sap.aii.adapter.mail.app/XIMailAdapterBean Local Enterprise Bean mail

Transform.Class com.sap.aii.messaging.adapter.Conversion

Transform.ContentDisposition attachment;filename="XHeaderName1"

Transform.ContentType text/plain;charset=utf-8

xml.DetailRecord.endSeparator 'nl'

xml.DetailRecord.fieldFixedLengths 6,2,3,18,40,13,5,15,15,15,15,8,10,6,35,8,13,10,8,6,13

xml.DetailRecord.fieldNames Delivery_Type,Sold_to,Sold_to_description,Issue_slip_number,Goods_movement_date,Delivery_item,Shipping_condition,Incoterms,Material_number,Material_description,Delivery_quantity,Currency,Gross_price,Total_discounts,Total_rises,Net_price,Sales_document_date,Sales_document_number,Document_item,PO_number,PO_date,Order_quantity,Invoice_number,Invoice_date,Invoice_item,Invoice_quantity

xml.DetailRecord.processFieldNames fromConfiguration

xml.addHeaderLine 0

xml.conversionType StructXML2Plain

xml.recordsetStructure DetailRecord

Thanks a lot!!

Fabio

shweta_walaskar2
Contributor
0 Kudos

Hi Fabio,

Your module configuration will only be:

sap.com/com.sap.aii.adapter.mail.app/XIMailAdapterBean Local Enterprise Bean mail

No need to use MessageTransformBean.

The only change as you use fieldfixedlengths ,which implies you dont need a delimiter,is to change the UDF to remove ; and just to concatenate the fields with a space in between.

UDF is already taking care of converting XML data to plain and the file type would depend on the value which you map to Content-Disposition,eg. attachment;filename="abc.txt"

Please let me know if it works.

Thanks.

Regards,

Shweta

Former Member
0 Kudos

Hi,

thanks a lot!!

ASMA and variable transport binding must be checked or not?

it raise an error in runtime workbench message monitoring:

2010-09-02 17:41:15 Success Mail: calling the adpter for processing

2010-09-02 17:41:15 Error Mail: call failed; com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {'}Content_Disposition at state 1

2010-09-02 17:41:15 Success Mail: sending a delivery error ack ...

2010-09-02 17:41:15 Success Mail: sent a delivery error ack

2010-09-02 17:41:15 Error Mail: error occured: com.sap.aii.af.ra.ms.api.RecoverableException: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {'}Content_Disposition at state 1

2010-09-02 17:41:15 Error MP: Exception caught with cause com.sap.aii.af.ra.ms.api.RecoverableException: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {}Content_Disposition at state 1

2010-09-02 17:41:15 Error Exception caught by adapter framework: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {}Content_Disposition at state 1

2010-09-02 17:41:15 Error Delivery of the message to the application using connection Mail_http://sap.com/xi/XI/System failed, due to: com.sap.aii.af.ra.ms.api.RecoverableException: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {}Content_Disposition at state 1.

This is my message in message monitoring:

<?xml version="1.0" encoding="UTF-8" ?>

- <ns1:Mail xmlns:ns1="http://sap.com/xi/XI/Mail/30">

<Content_Disposition>"attachment; filename="MyFileName.txt"</Content_Disposition>

<Content>ZLF;0001000079;Dealer Motors UK</Content>

</ns1:Mail>

In message mapping with target message mail package I've linked Content_Disposition with the constant

"attachment; filename="MyFileName.txt"

If I cancel this relation the mail arrives correctly.

One other thing: when I took mail.xsd from SAP the fields Content_Disposition and Content_Description weren't in, so I added them manually in XSD.

thanks

Edited by: Fabio Boni on Sep 2, 2010 5:42 PM

Edited by: Fabio Boni on Sep 2, 2010 6:06 PM

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

You shouldn't change Mail.xsd.

There is a new version available for Mail.xsd which has these fields.

Please use the same.You will not get this error again.

Please let me know.

Thanks.

Regards,

Shweta

Former Member
0 Kudos

Hi,

now I'm using new version of mail.xsd but same error came. Any suggestions?

In message mapping from target to mail I've linked:

Mail_address_to (input field from payload) --> setMailParameters (UDF to set FROM and TO fields) --> ns1:Mail

Constant: attachment; filename="MyFileName.txt" --> Content_Disposition

All mapping fields --> ConcatValues --> Create Contest --> Content

IF i cancel the second relation it works.

Again the error:

2010-09-03 10:18:39 Error Mail: error occured: com.sap.aii.af.ra.ms.api.RecoverableException: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {'}Content_Disposition at state 1

2010-09-03 10:18:39 Error MP: Exception caught with cause com.sap.aii.af.ra.ms.api.RecoverableException: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {}Content_Disposition at state 1

2010-09-03 10:18:39 Error Exception caught by adapter framework: com.sap.aii.messaging.util.XMLScanException: expecting end tag: Mail, but found {}Content_Disposition at state 1

and the payload of message:

<?xml version="1.0" encoding="UTF-8" ?>

- <ns1:Mail xmlns:ns1="http://sap.com/xi/XI/Mail/30">

<Content_Disposition>attachment; filename="MyFileName.txt"</Content_Disposition>

<Content>ZLR;0001000079;Dealer Motors UK</Content>

</ns1:Mail>

Thanks

Fabio Boni

Edited by: Fabio Boni on Sep 3, 2010 10:31 AM

Edited by: Fabio Boni on Sep 3, 2010 10:31 AM

Edited by: Fabio Boni on Sep 3, 2010 10:32 AM

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

I hope,I got the error now.

When you use mail package,you have to map FROM and TO fields which are mandatory,I think,you have not mapped FROM and TO.You can map ns1:Mail to your MT_... node (Root node of target structure)

You are mapping:

Mail_address_to (input field from payload) --> setMailParameters (UDF to set FROM and TO fields) --> ns1:Mail

instead ,you should divide setMailParameters into two UDFs : setFROM and setTO and map these to FROM and TO fields ,respectively.

The current mapping is making your Mail XML structure invalid and hence you are getting this error.

Let me know if it helps.

Regards,

Shweta

Former Member
0 Kudos

Hi,

It works!!!

thanks for your great help!!

I've cancelled the UDF SetMailParameters and linked directly my input field mail_address_to to TO field and then linked a constant address to FROM field.

Also I've linked my MT to ns1:Mail.

I've still little problems to solve:

1) Despite the records in input message are 15, in the resulting attachment there only 1 line in content field, the first. Any suggestions? maybe something that I done wrong in UDF?

2) The maximum number of arguments for an user-defined function is 20? I've more than 20 field to use as input of Concat Value but with edit function I cannot add more than 20 arguments.

Thanks

Fabio Boni

shweta_walaskar2
Contributor
0 Kudos

Hi Fabio,

Nice to know that it works.

For 1) Despite the records in input message are 15, in the resulting attachment there only 1 line in content field, the first. Any suggestions? maybe something that I done wrong in UDF?

public void createContent(String[] a,ResultList result,Container container){

AbstractTrace trace = container.getTrace();

String str = "";

for(int i=0;i<a.length;i++)

{

if(i == (a.length-1))

str = str + a;

else

str = str + a + "\n";

}

result.addValue(str);

This is a UDF of type context.I hope in statements str = str + a; and str = str + a + "\n"; , you have not used just 'a', instead you have used an array field a with index i like:

if(i == (a.length-1))

str = str + a; else str = str + a + "\n";

////Please change curly bracket with square bracket as for standard Java array elements,the problem is when I post it on SDN,index element goes off.

str = str + a + "\n"; takes care of concatenating all records.

2) The maximum number of arguments for an user-defined function is 20? I've more than 20 field to use as input of Concat Value but with edit function I cannot add more than 20 arguments.

I understand,please create multiple concatValue functions ,say concatValue1,concatValue2,concatValue3 and one concatValueAll

Suppose you have 30 fields, use concatValue1 to concatenate first 10 fields ,concatValue2 to concatenate next 10 fields and concatValue3 to concatenate last 10 fields

concatValueAll should have 3 arguments then and pass output of concatValue1,concatValue2 and concatValue3 to concatValueAll .

Does it make sense?

Let me know.

Regards,

Shweta

Former Member
0 Kudos

Hi,

for 2) I imagined that solution, no problem.

for 1) my function is

public void CreateContent(String[] a,ResultList result,Container container){

AbstractTrace trace = container.getTrace();

String str = "";

for(int i=0;i<a.length;i++)

{

if(i == (a.length-1))

str = str + a{i};

else

str = str + a + "\n" ;

}

result.addValue(str);

}

but still 1 line

Regards

Fabio

Edited by: Fabio Boni on Sep 3, 2010 12:02 PM

Edited by: Fabio Boni on Sep 3, 2010 12:02 PM

Edited by: Fabio Boni on Sep 3, 2010 12:04 PM

Edited by: Fabio Boni on Sep 3, 2010 12:04 PM

Former Member
0 Kudos

I try to use Remove context and it works, but 15 records are all in 1 line with a square as separator.

input field -->Remove context --> concat value

same thing happens if I change the context for each field (from Detail Record to MT...)

maybe is not the right solution...

Edited by: Fabio Boni on Sep 3, 2010 12:23 PM

Edited by: Fabio Boni on Sep 3, 2010 12:36 PM

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

It should be :

Input field(No change in context for input field)-> mapWithDefault-> concatValue -> removeContexts -> createContent - > Target field

If you don't use mapWithDefault and one of the field doesn't exist in record,Content would be set to SUPPRESS.

Have you already tried this?

Regards,

Shweta

Former Member
0 Kudos

Hi,

tried but problem still remains.

Maybe is the carriage return value "\n" that is not correct for my requirement.

I'm creating a txt file and I open it with notepad. Opening with notepad shows only one line with 15 record separated by a square box, but if I open the file with textpad it'ok, 15 lines.

Thanks

Fabio

Edited by: Fabio Boni on Sep 3, 2010 2:50 PM

shweta_walaskar2
Contributor
0 Kudos

Hello Fabio,

Please go through this note:

On Windows platforms, the line separator is CRLF (carriage return / line feed), which is "\r\n". On Unix platforms, it's just LF, "\n". Traditionally, on Apple platforms it has been just CR, "\r". Which is why it's so important when you're building a platform-independent application (which is always, unless you have a distinct reason not to) to use Java's built in ways of doing these things, as mentioned above.

Opening up a text file in Notepad that uses just "\n" or just "\r" causes Notepad to display an invalid character, which was that box that you saw.

Can you please try to use \r\n instead of just \n in UDF?

Regards,

Shweta

Former Member
0 Kudos

Hi,

now is

AbstractTrace trace = container.getTrace();

String str = "";

for(int i=0;i<a.length;i++)

{

if(i == (a.length-1))

str = str + a{i};

else

str = str + a+ "\r\n" ;

}

result.addValue(str);

but same problem

shweta_walaskar2
Contributor
0 Kudos

Strange...

Which platform is this?

in our case, \n works. Atleast one of \r , \n or \r\n should work

Regards,

Shweta

Former Member
0 Kudos

Hi,

it's windows.

\r, \n and \r\n don't work

shweta_walaskar2
Contributor
0 Kudos

Hi Fabio,

I have no solution to this at the moment.I will try to search if we can find one.

Regards,

Shweta

Former Member
0 Kudos

Hi,

I close this thread cos problem of setting dynamic attachment name in mail adapter is solved.

Then I'll open a new thread for notepad problem.

Thanks for your help!

Regards

Fabio Boni

Former Member
0 Kudos

Hi Shweta,

I have a scenario where PI has to read different kind of files (Text/Image/pdf) from a file directory and send it to email as an attachment with the same file name and file type.

Could you please give me some idea how to acheive this?

Thanks-
Rams

Former Member
0 Kudos

Hi Fabio,

I have a scenario where PI has to read different kind of files (Text/Image/pdf) from a file directory and send it to email as an attachment with the same file name and file type (No mapping is required but simply PI has to move the files to mails as an attachments).

Could you please give me your views/points to be followed to achieve this solution?

Thanks-
Rams

nabendu_sen
Active Contributor
0 Kudos

Hi Rams,

Please go through the blog. It has everything to implement your requirement.

http://wiki.scn.sap.com/wiki/pages/viewpage.action?spaceKey=ESOAInfrastructure&original_fqdn=wiki.sd...

Regards,

Nabendu.

Answers (0)