Thank you Steve! I implemented your hiddenGroup idea. See DFDL schema below.

For this input:

.../09190935Z/...

DFDL parsing produces this XML output:

<Test>
  <A>...</A>
  <DateTimeIso>2023-09-19T09:35:00+00:00</DateTimeIso>
  <B>...</B>
</Test>

DFDL unparsing produces this:

.../09190935Z/...

Wicked cool!

Here is my DFDL schema:

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:dfdl=http://www.ogf.org/dfdl/dfdl-1.0/
           xmlns:xs=http://www.w3.org/2001/XMLSchema
           xmlns:fn=http://www.w3.org/2005/xpath-functions>
    <xs:annotation>
        <xs:appinfo source=http://www.ogf.org/dfdl/>
            <dfdl:format alignment="1"
                alignmentUnits="bytes"
                choiceLengthKind="implicit"
                emptyValueDelimiterPolicy="none"
                encoding="ASCII"
                encodingErrorPolicy="replace"
                escapeSchemeRef=""
                fillByte="%SP;"
                floating="no"
                ignoreCase="yes"
                initiatedContent="no"
                initiator=""
                leadingSkip="0"
                lengthKind="delimited"
                lengthUnits="characters"
                nilValueDelimiterPolicy="none"
                occursCountKind="implicit"
                outputNewLine="%CR;%LF;"
                representation="text"
                separator=""
                separatorSuppressionPolicy="anyEmpty"
                sequenceKind="ordered"
                textBidi="no"
                textPadKind="none"
                textTrimKind="none"
                trailingSkip="0"
                truncateSpecifiedLengthString="no"
                terminator=""
                textNumberRep="standard"
                textStandardBase="10"
                textStandardZeroRep="0"
                textNumberRounding="pattern"
                textStandardExponentRep="E"
                textNumberCheckPolicy="strict"/>
        </xs:appinfo>
    </xs:annotation>
    <xs:element name="Test">
        <xs:complexType>
            <xs:sequence dfdl:separator="/" dfdl:separatorPosition="infix">
                <xs:element name="A" type="xs:string" />
                <xs:sequence dfdl:hiddenGroupRef="hidden-MonthDayTime" />
                <xs:element name="DateTimeIso" type="xs:dateTime"
                    dfdl:inputValueCalc="{
                        
xs:dateTime(fn:concat('2023',fn:substring(xs:string(../hidden),5)))
                    }"/>
                <xs:element name="B" type="xs:string" />
            </xs:sequence>
        </xs:complexType>
    </xs:element>

    <xs:group name="hidden-MonthDayTime">
        <xs:sequence>
            <xs:element name="hidden" type="xs:dateTime"
                dfdl:calendarPatternKind="explicit"
                dfdl:calendarCheckPolicy="strict"
                dfdl:calendarPattern="MMddHHmmX"
                dfdl:calendarFirstDayOfWeek="Monday"
                dfdl:calendarDaysInFirstWeek="7"
                dfdl:calendarTimeZone="UTC+6"
                dfdl:calendarLanguage="en"
                dfdl:outputValueCalc="{
                    ../DateTimeIso
                }"/>
        </xs:sequence>
    </xs:group>

</xs:schema>



From: Steve Lawrence <slawre...@apache.org>
Sent: Friday, November 3, 2023 2:23 PM
To: users@daffodil.apache.org
Subject: [EXT] Re: Is there a way to insert an implied year into a 
month-day-time input value?

Nope, details from the environment Daffodil runs in are never supposed to be 
used for making parsing decisions. So whether you run Daffodil on a machine in 
2023 or 2024, you'll always get the same result. Note that you can give your 
xs: dateTime


Nope, details from the environment Daffodil runs in are never supposed

to be used for making parsing decisions. So whether you run Daffodil on

a machine in 2023 or 2024, you'll always get the same result.



Note that you can give your xs:dateTime and a pattern that does not

include a year field, but the spec says:



 > When parsing, for any pattern that omits components the values for the

 > omitted components are supplied from the Unix epoch

 > 1970-01-01T00:00:00.000.[44]



So you would get the year 1970 in the infoset, so not particularly

useful if 2023 is supposed to be implied.



One option would be to parse the month/day components separately as

integers, and then parse the time separately as a xs:dateTime.



Another option, but more complex, would be to parse the field as a

hidden xs:dateTime with a missing year component from the

dfdl:calendarPattern, and then use an inputValueCalc on another element

with an expression to change the year from 1970 to 2023. Something like:



   <element name="hidden" ... dfdl:calendarPattern="MMddHHmmssX" />

   <element name="field" ... dfdl:inputValueCalc="{

xs:dateTime(fn:concat('2023', fn:substring(../hidden, 5))) }"



And if you wanted '2023' to be the current year, you could replace that

with an externally defined variable, and users calling parse would be

expected to set that to the current year.





That said, maybe an interesting extension property could be added to

define a different value for replacement components, e.g.



   dfdlx:calendarReplacementComponents="2023-01-01T00:00:00.000"



Not a good name, but that's the idea. This would give you the 2023 year

you expect in the infoset instead of 1970. You would still need to

either change that property every year, or use a externally defined

variable and pass in the current year like mentioned above.





On 2023-11-03 01:39 PM, Roger L Costello wrote:

> My input contains a month-day-hour-minute-timezone, e.g.,

>

> .../09190935Z/...

>

> I believe that the current year (2023) is implied. Is there a way to add the 
> current year so that the result of parsing is the standard datetime format?  
> E.g.,

>

> <TimeOfReturnToOperations>2023-09-19T09:35:00+00:00</TimeOfReturnToOperations>

>

> /Roger


Reply via email to