@@ -135,12 +135,17 @@ if (!test_longdouble) {
135135# generate simple error messages from base that are checked against in our tests. this helps
136136# protect us against these messages evolving in base in the future, and against these messages
137137# potentially not being produced in English.
138+ # If the target condition only appears on certain platforms/R versions, this will return NULL
139+ # whenever the code succeeds, or the message matcher wherever it fails. Thus we can flexibly
140+ # pass e.g. 'warning = NULL | warning = <warning>' concisely as 'test(., warning = get_msg())'.
138141# Three use cases:
139142# (1) match message exactly [missing delim]
140143# (2) match message pattern after dropping anything between delimeters [delim, fmt=FALSE]
141144# (3) function factory for matching messages exactly by substituting anything between delimeters [delim, fmt=TRUE]
142145get_msg = function(e, delim, fmt=FALSE) {
143- msg = tryCatch(e, error=identity, warning=identity)$message
146+ condition = tryCatch({e; NULL}, error=identity, warning=identity)
147+ if (is.null(condition)) return(condition)
148+ msg = condition$message
144149 if (missing(delim)) return(msg)
145150 if (length(delim) == 1L) delim[2L] = delim[1L]
146151 msg = gsub(
@@ -165,7 +170,8 @@ base_messages = list(
165170 missing_file = get_msg({tmp <- tempfile(tmpdir=tempfile("xxx")); file(tmp, "w")}, "'"),
166171 # gives both error & warning but tryCatch returns the warning first, so suppress
167172 cant_open_file = get_msg(suppressWarnings({con<-file(tempfile()); open(con, 'r')})),
168- mixed_subscripts = get_msg(letters[-1:1])
173+ mixed_subscripts = get_msg(letters[-1:1]),
174+ maybe_invalid_old_posixct = get_msg(as.POSIXct("1893-12-28 05:15:36", tz = ""))
169175)
170176
171177##########################
@@ -16854,8 +16860,17 @@ if (.Platform$OS.type!="windows") {
1685416860 # blank TZ env variable on non-Windows is recognized as UTC consistent with C and R; but R's tz= argument is the opposite and uses "" for local
1685516861}
1685616862Sys.unsetenv("TZ")
16857- tt = fread(tmp, colClasses=list(POSIXct="times"), tz="") # from v1.14.0 tz="" needed
16858- test(2150.025, attr(tt$times, "tzone"), "") # as.POSIXct puts "" on the result (testing the write.csv version here with missing tzone)
16863+ # Notes:
16864+ # - from v1.14.0 tz="" needed
16865+ # - as.POSIXct puts "" on the result (testing the write.csv version here with missing tzone)
16866+ # - Per #5866, this test is complicated by some interaction with very specific builds of R where
16867+ # as.POSIXct() might fail for very old timestamps when 'tz=""' is used. On such systems,
16868+ # as.POSIXct() failure means 'times' is returned as a character, hence no 'tzone' attribute.
16869+ # fread() will also throw a warning, one substring of which will be the reproduced base R error.
16870+ test(2150.025,
16871+ attr(fread(tmp, colClasses=list(POSIXct="times"), tz="")$times, "tzone"),
16872+ if (is.null(base_messages$maybe_invalid_old_posixct)) "" else NULL,
16873+ warning=base_messages$maybe_invalid_old_posixct)
1685916874# the times will be different though here because as.POSIXct read them as local time.
1686016875if (is.na(oldtz)) Sys.unsetenv("TZ") else Sys.setenv(TZ=oldtz)
1686116876fwrite(copy(DT)[ , times := format(times, '%FT%T+00:00')], tmp)
0 commit comments