Pins the DATE file-metadata key to a fixed value, so that writing the same data twice
produces BYTE-IDENTICAL files. Blank (the factory default) restores reading the clock.
What this is for. Every file this library writes carries a creation timestamp, and that
timestamp is the only thing that differs between two writes of the same data -- measured, by
writing one file forty times: runs landing in the same wall-clock second are bit-identical,
and runs a second apart differ in nine bytes, every one of them a seconds digit. Pinning it
is therefore the whole of what byte-for-byte reproducibility needs, which is what makes this
knob worth having for a regression suite, a build system or a diff between two runs.
It PINS the date, it does not remove it. The key is still written, at its declared width,
in all four places the timestamp appears -- the DATE key, the VOTable sidecar's own
DATE PARAM, and both of those again inside the base64 ARROW:schema blob, which Arrow
duplicates from the key-value metadata. Suppressing the key instead was considered and
rejected: DATE is written unconditionally by design and SHADOWS a user's own
schema%add_metadata("DATE", ...) on read, so removing it would silently promote the user's
entry and change what an unrelated call answers.
text must be blank, or exactly 19 characters in the form YYYY-MM-DDTHH:MM:SS with each
field in range; anything else aborts. The width is not a preference -- see file_date_len.
Read when a WRITER IS OPENED, not when it is closed, like every other C++-side knob:
parquet_open_writer pushes the mirror (see parquet_push_settings_to_cpp). Set it before
opening the writer, which is the contract doc/pages/operating/settings.md already states for
settings generally.
| Type | Intent | Optional | Attributes | Name | ||
|---|---|---|---|---|---|---|
| character(len=*), | intent(in) | :: | text |
"YYYY-MM-DDTHH:MM:SS", or "" to read the clock. |
subroutine parquet_set_file_date(text) character(len=*), intent(in) :: text !! "YYYY-MM-DDTHH:MM:SS", or "" to read the clock. character(len=:), allocatable :: got, why got = trim(adjustl(text)) if (len(got) == 0) then cfg_file_date = "" return end if call file_date_problem(got, why) if (len(why) > 0) then ! Capped preview, never the whole value: `text` is caller-supplied and unbounded, and ! ifx's ERROR STOP runtime corrupts the heap once the composed message reaches 8192 ! bytes -- the same rule parquet_filter_add follows. if (len(got) > 100) got = got(1:100) // "..." error stop "parquet_set_file_date: '" // got // "' is not a valid file date -- " // & why // " (expected YYYY-MM-DDTHH:MM:SS, or an empty string to use the clock)" end if cfg_file_date = got end subroutine parquet_set_file_date