cancel
Showing results for 
Search instead for 
Did you mean: 

File2IDoc - new IDoc when client-number in sub-segment of MT is different

Former Member
0 Kudos

Hi, we have an Message-Type and IDoc with four different Segments. Each of it contains a client-number.

First segment: Header

Second-fouth: Childs

When i read File via FTP in XI it could happen that the Header-Segment is not depending on the child. That is when the client-number in the text-file is different. When this happens, XI should create a new IDoc where no Header-Segment will occur.

How should i manage this in mapping? i have to read the payload and must compare the client-number of each child in the txt-file.

Could you give me some help?!

This is the source-structure:

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

<MT_BESTFILE>

<BestfileRecordSet>

<BestFileHeader>

<BDKDNR/> (=client-number)

[...]

</BestFileHeader>

<BestFilePos>

<BDKDNR/>(=client-number)

[...]

</BestFilePos>

<BestFilePos1>

<BDKDNR/>(=client-number)

[...]

</BestFilePos1>

<BestFilePos2>

<BDKDNR/>(=client-number)

[...]

</BestFilePos2>

</BestfileRecordSet>

</MT_BESTFILE>

Accepted Solutions (0)

Answers (8)

Answers (8)

Former Member
0 Kudos

Hi Carsten,

This problem can be solved but to explain to you i want the idoc structure to which you are mapping. so that i can clearly explain you how to map the fields in idoc from your input structure.

And also please provide me the info about which field in source structure is to be mapped to which field in target structure.

it would be very helpful if you could mail me the above info to chirumamilla.sukarna@accenture.com

i can respond to your mail at the earliest.

Regards,

Karan.

Former Member
0 Kudos

Hi Carsten,

Below UDF will solve your problem,

Here it will take input as BDKDNR from Header, Pos, Pos1 and Pos2, and output should be mapped to IDOC Header so that it will create a new idoc when ever there is a change in child segment.

as per your query it is clear that BDKDNR from header will match with child segments but some times it will differ at that point we should create a new IDOC.

in the UDF header BDKDNR will be compared to the child BDKDNR's if it is not matching with the header then it will create a new idoc.

Please let me know it the problem still exits.

public void test(String[] header,String[] pos,String[] pos1,String[] pos2,ResultList result,Container container){

int i,j,count=0;

for(i=0;i<header.length;i++)

{

result.addValue(header<i>);

}

for(j=0;j<pos.length;j++)

{

for(i=0;i<header.length;i++)

{

if(!(pos[j].equals(header<i>)))

{

count++;

}

}

if(count>0)

{

result.addValue(pos[j]);

count=0;

}

}

for(j=0;j<pos1.length;j++)

{

for(i=0;i<header.length;i++)

{

if(!(pos1[j].equals(header<i>)))

{

count++;

}

}

if(count>0)

{

result.addValue(pos1[j]);

count=0;

}

}

for(j=0;j<pos2.length;j++)

{

for(i=0;i<header.length;i++)

{

if(!(pos2[j].equals(header<i>)))

{

count++;

}

}

if(count>0)

{

result.addValue(pos2[j]);

count=0;

}

}

}

Regards,

Karan

Former Member
0 Kudos

Hi Karan,

well ur code looks good so far. But because i am not experienced in Java UDF i need the imports for using this code...

java.lang., java.util., java.io.* and java.lang.reflect.* i don't need, so what is missing?!

i am getting this error: ..../j2ee/cluster/server0/./temp/classpath_resolver/Map2f0a60f09c2311dca54c000ae4821300/source/com/sap/xi/tf/_MT_BESTFILE_to_ZBC13_BESTFILE_.java:276: 'class' or 'interface' expected....

can u help.. ?

br

Former Member
0 Kudos

Forget about last post, it was a missing bracket

But now i have this:

addValue(java.lang.String) in com.sap.aii.mappingtool.tf3.rt.ResultList cannot be applied to (java.lang.String[]) result.addValue(header);

Don't get it because header is of type String[]!

br

Former Member
0 Kudos

Hi Carsten,

When you create a UDF you have 3 radio buttons. Choose Context from that and try.

Regards,

Kumar.

Former Member
0 Kudos

Hi, well i made it. there was one thing missing:

result.addValue(header<b><i></b>);

But now the problem is that an IDoc is generated but the childnodes are missing. This means that for each occurence of a new BDKDNR number the IDoc should be new and of course the child-nodes...

br Carsten

Former Member
0 Kudos

HI carsten,

i tried it and it didn't work, i am trying to write an UDF, in the UDF i am going to check the header BDKDNR with POS, POS1 and POS2 BDKDNR, so that if header BDKDNR is not matching with any of the child BDKDNR then it should create a new idoc.

please correct me if my understanding is wrong.

Regards,

Karan.

Former Member
0 Kudos

Hi Carsten,

i am just confused on your mapping...r u using graphical mapping for this or Java??

if it is Graphical mapping then there is no need for you to check the child segments the split by value function will automatically checks that, and creates a new idoc when ever there is a value change.

Because we are changing the context to top node.

Regards,

karan.

Former Member
0 Kudos

Yes it's graphical mapping. Just to make sure:

This is my Source-structure:

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

<ns:MT_BESTFILE xmlns:ns="http://de.xi.hatz-diesel/as400">

<BestfileRecordSet>

<BestFileHeader/>

<BestFilePos/>

<BestFilePos1/>

<BestFilePos2/>

</BestfileRecordSet>

</ns:MT_BESTFILE>

The <BestFilePos/>, <BestFilePos1/>, <BestFilePos2/> i have to map to <IDOC BEGIN="">?! This isn't working even though i had changed occurence of the IDoc.

Actually for each of the BestFile-Segments it has to be checked what value of <BDKDNR> is given, than a new IDoc has to be generated.

With ur suggestion it is not working only because that i can only map ONE Segment to the IDoc-Node, not four ( because of BestFileHeader and BestFilePos,BestFilePos1,BestFilePos2).

br

Former Member
0 Kudos

Hi Carsten,

could you try this,

1) Map the BDKDNR to the IDOC node and change the context of BDKDNR to MT_XXXXXX (the top node in your MT) as Sachin said.

2) in Mapping use splitbyvalue function between BDKDNR and IDOC node. Right click the splitbyvalue function and in properties of splitbyvalue you change the property to "value changed"

Hope this works.

Regards,

Karan.

Former Member
0 Kudos

Hi Chiru,

i tried as u suggested but it is not working out. Here is my mapping

/ZBC13_BESTFILE/IDOC=SplitByValue([type=Value changed]stringEquals(/MT_BESTFILE/BestfileRecordSet/BestFilePos1/BDKDNR=, /MT_BESTFILE/BestfileRecordSet/BestFilePos/BDKDNR=))

to explain the stringEquals: in source there are 3 different child segments (BestFielPos to BestFilePos2) in which i have to check wether the BDKDNR is alwas the same, otherwise new IDoc!!

can u help? br

Former Member
0 Kudos

hi Sachin,

i think if you map field BDKDNR ot the idoc node it will create idocs for all the segments in the XML. but carsten wants an idoc when BDKDNR changes, i.e. one idoc for all 7179 and one for 7100.

is my understanding correct Carsten???

Former Member
0 Kudos

@ Chiru

yes you understand the problem. BDKDNR is changing sometimes. Therefore a new IDoc should be generated!

any ideas?

former_member214364
Active Contributor
0 Kudos

Hi Carsten,

Do you want to compare Client number in Header with Client number of each child node? if you could give sample source payload and source message type(With node occurrences) i can help you in mapping.

i look forward to hearing from you.

Cheers,

Jag

Former Member
0 Kudos

Hi Jag,

well source MT i posted in my previous post. There u can see Tag <BDKDNR> which could be different in child nodes. so in payload sometimes a header-segment of the MT occurs but sometimes don't, than a new Idoc should be generated.

Here is some example payload which is read by File-Adapter:

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

<ns:MT_BESTFILE xmlns:ns="http://de.xi.XY">

<BestfileRecordSet>

<BestFileHeader>

<BDKDNR>7179</BDKDNR>

<BDDSKNR>609</BDDSKNR>

<BDART>T</BDART>

<DATA>1 PLEASE SHIP VIA EGE-TRANS STANDARD AI</DATA>

</BestFileHeader>

<BestFileHeader>

<BDKDNR><b>7179</b></BDKDNR>

<BDDSKNR>609</BDDSKNR>

<BDART>T</BDART>

<DATA>4 THANK YOU STEVE Z</DATA>

</BestFileHeader>

<BestFilePos>

<BDKDNR><b>7179</b></BDKDNR>

<BDDSKNR>378</BDDSKNR>

<BDART>S</BDART>

<BDIDENT>50048100</BDIDENT>

<BDMENGE>0000002</BDMENGE>

<BDFREMD></BDFREMD>

</BestFilePos>

<BestFilePos1>

<BDKDNR><b>7100</b></BDKDNR>

<BDDSKNR>609</BDDSKNR>

<BDART>L</BDART>

<BDIDENT>00585101</BDIDENT>

<BDMENGE>0000010</BDMENGE>

<BDFREMD></BDFREMD>

</BestFilePos1>

</BestfileRecordSet>

</ns:MT_BESTFILE>

As u can see, the BDKDNR as client-number changes in the child-segments. So when a new client number shows up, a new Idoc should be generated!

Can u help? I highly appreciate ur help!

br

former_member184619
Active Contributor
0 Kudos

hi,

it can be achived....

just map the field <BDKDNR> to the node IDOC in the target....i.e.

each time field <BDKDNR> occurs a new idoc will bw generated. but for that the idoc should have occurance more than one..

check this for changing occurance trick

/people/michal.krawczyk2/blog/2005/12/04/xi-idoc-bundling--the-trick-with-the-occurance-change

Sachin

former_member184619
Active Contributor
0 Kudos

i misunderstood the problem...

the above solution is for how to create a new idoc when a new line item occurs. Ignore it if it's is of no use

Former Member
0 Kudos

No one?! am i too lame?!