Author |
Message
|
McueMart |
Posted: Wed Sep 30, 2015 1:45 am Post subject: DFDL - compare byte value in Discriminator |
|
|
 Chevalier
Joined: 29 Nov 2011 Posts: 490 Location: UK...somewhere
|
Hi,
Im trying to use a literal byte value in a discriminator.
I am trying to test if the value is the 0x0a (LF) byte.
I have managed to get it to work using this syntax:
{xs:string(../LFFiller) eq '0A'}
But I wanted to find a way which avoided the casting of the byte to string.
I have tried the following:
{../LFfiller eq '%#r0a;'}
Which uses the byte value entity as defined on:
https://www-01.ibm.com/support/knowledgecenter/SSKM8N_8.0.0/com.ibm.dfdl.spec.doc/dfdl_6_3.htm
But that didnt work (See trace below):
Code: |
30 Sep 2015 10:32:44 info: Offset: 1127. Found binary fixed length value: x'0A' for element 'LFfiller'.
30 Sep 2015 10:32:44 info: Offset: 1128. The simple content region of element 'LFfiller' was converted to logical value '0A'.
30 Sep 2015 10:32:44 info: Offset: 1128. Finished processing element 'LFfiller'.
30 Sep 2015 10:32:44 info: Offset: 1127. Attempting expression '{../LFfiller eq '%#r0a;'}' for element 'LFfiller'.
30 Sep 2015 10:32:44 info: CTDV1558E : Incompatible operand types : DFDL expression '{../LFfiller eq '%#r0a;'}' cannot be evaluated because the operands supplied to XPath operator 'eq' must be of compatible types |
Any help much appreciated! |
|
Back to top |
|
 |
timber |
Posted: Thu Oct 01, 2015 12:18 am Post subject: |
|
|
 Grand Master
Joined: 25 Aug 2015 Posts: 1292
|
There are two types of DFDL discriminator, distinguished by the 'testKind' attribute.
See section 7.4.1 in the DFDL specification:
https://www-01.ibm.com/support/knowledgecenter/SSMKHH_10.0.0/com.ibm.dfdl.spec.doc/dfdl_index.htm
* testKind='expression'
Applies the XPath expression in the 'test' attribute to the DFDL infoset ( a.k.a. the message tree )
* testKind='pattern'
Applies the regex in the 'testPattern' attribute to the input bitstream
So if you are matching a literal byte value, then either
a) you must model the field as xs:hexBinary and use testKind='expression'
or
b) you must use testKind='pattern' to test the raw, unparsed bytes at the current position in the input bitstream.
What you cannot do is apply an XPath to unparsed byte values. XPath is for logical data, not the bitstream ( which is why testKind=pattern was added to the DFDL specification ). |
|
Back to top |
|
 |
McueMart |
Posted: Thu Oct 01, 2015 12:47 am Post subject: |
|
|
 Chevalier
Joined: 29 Nov 2011 Posts: 490 Location: UK...somewhere
|
Thanks for that.
So now for the life of me I cant figure out how to set a testKind of 'pattern' on the discriminator (Im using the 8.0.0.6 toolkit). It seems like expression is the only option I can configure. |
|
Back to top |
|
 |
McueMart |
Posted: Thu Oct 01, 2015 12:48 am Post subject: |
|
|
 Chevalier
Joined: 29 Nov 2011 Posts: 490 Location: UK...somewhere
|
"Only discriminators with test expressions are supported in the current IBM DFDL implementation"
I guess that's why? |
|
Back to top |
|
 |
timber |
Posted: Thu Oct 01, 2015 4:09 am Post subject: |
|
|
 Grand Master
Joined: 25 Aug 2015 Posts: 1292
|
Quote: |
I wanted to find a way which avoided the casting of the byte to string |
If you cannot upgrade to a version of IIB that supports testKind=pattern then you may need to do that. If you choose a fully-populated encoding like ISO8859-1 then it should be safe ( no decoding errors because every byte has a valid character associated with it ). |
|
Back to top |
|
 |
McueMart |
Posted: Fri Oct 02, 2015 1:53 am Post subject: |
|
|
 Chevalier
Joined: 29 Nov 2011 Posts: 490 Location: UK...somewhere
|
Quote: |
If you choose a fully-populated encoding like ISO8859-1 then it should be safe ( no decoding errors because every byte has a valid character associated with it ). |
The xs:string(..) seems to be converting the byte to it's hexadecimal string representation i.e. '0A' (hence why {xs:string(../LFFiller) eq '0A'} works) so im hoping I don't have to worry about encoding's full stop here!
Thanks for your help though. Good to know in later versions of IIB there is this more efficient approach. |
|
Back to top |
|
 |
timber |
Posted: Fri Oct 02, 2015 2:55 am Post subject: |
|
|
 Grand Master
Joined: 25 Aug 2015 Posts: 1292
|
Quote: |
The xs:string(..) seems to be converting the byte to it's hexadecimal string representation |
You sound surprised...
There is a public specification for the XPath language, and the behaviour of the string constructor is described here:
http://www.w3.org/TR/xpath-functions/#constructor-functions
where is says:
"The semantics of the constructor function " xs:TYPE(arg) " are identical to the semantics of " arg cast as xs:TYPE? ". See 17 Casting."
So we follow the link, and find...
http://www.w3.org/TR/xpath-functions/#casting-to-string
"...In all other cases, TV is the [XML Schema Part 2: Datatypes Second Edition] canonical representation of SV. "
Your source data type is xs:hexBinary, so the result of xs:string(yourValue) will be the XML Schema canonical representation of the hexBinary string. Which is exactly what you seem to be getting.
Not straightforward, I'll admit. But it's sometimes useful to go back to the specification in cases like this. |
|
Back to top |
|
 |
McueMart |
Posted: Fri Oct 02, 2015 3:04 am Post subject: |
|
|
 Chevalier
Joined: 29 Nov 2011 Posts: 490 Location: UK...somewhere
|
Darn, now why didn't I figure that out
Thanks for the explanation!  |
|
Back to top |
|
 |
|