Skip to contents

unexcel 0.2.0

This release removes the guesswork. Version 0.1.0 worked only from imported values and had to infer three things it could not know: which numbers were serials, which date system produced them, and whether the day or the month came first. An .xlsx file answers all three about itself, so unexcel now reads the workbook instead.

Reading the workbook

  • unexcel_xlsx() reads a worksheet and undoes its date auto-conversion using only what the file states: the date system from xl/workbook.xml and each cell’s number format from xl/styles.xml. A cell is restored because the workbook formats it as a date, never because its magnitude falls in a plausible range — so an ordinary number that happens to look like a serial is left alone, and a serial outside the expected range is still recovered. No threshold, year window or reference date is involved.
  • excel_date_system() reports the date system a workbook declares, ending the four-years-and-a-day ambiguity between the 1900 and 1904 systems.
  • excel_date_cells() lists every date-formatted cell with its serial, resolved date, number format code and restored value — an audit trail that can be checked before any value changes.
  • excel_date_columns() summarises the same information per column, so a frame imported with readxl, openxlsx or anything else can be repaired with nothing left to infer.
  • excel_sheets() lists the sheets in a workbook.
  • The day/month order is taken from each column’s format code, so d/m/yyyy and m/d/yy columns are handled correctly without being told.

The conversion itself

  • serial_to_day_month() exposes the exact conversion: given a serial, a date system and a field order there is one answer and no inference. Every other function reduces to it.
  • excel_origin() returns the origin date behind each system.
  • All conversions gain output = "character", which preserves a trailing zero. A value typed as 3.10 is the number 3.1, and only the character form can tell it from a value typed as 3.1.

Working from imported values

  • restore_day_month() gains date_system and order, which should be supplied rather than inferred. date_system defaults to "1900", what every current Excel writes.
  • Breaking: origin_mode is deprecated and no longer the way to choose a date system. "1900" and "1904" are still accepted and forwarded to date_system. origin_mode = "auto" — the 0.1.0 default — still works but now warns: it picked the date system by comparing candidate dates against ref_date, which is a heuristic that can be wrong by four years and a day. Calls that relied on the old default now use the 1900 system.
  • fix_serial_columns() gains cols, which names the columns to repair and turns off the pmin scan, and the same date_system, order and output arguments.
  • Documentation now separates what is exact from what is assumed, in every function that assumes anything.

Package

  • New dependency: xml2, for reading the workbook parts.
  • Example workbooks in inst/extdata/, including one that declares the 1904 system and one column of ordinary numbers inside the serial range.
  • A testthat suite covering the parser, the format-code classifier, both date systems, and the agreement between the file-driven and value-driven paths.
  • New vignette excel-date-systems, explaining serials, the 1900 leap-year bug, and how number formats are read. The former unexcel vignette is now getting-started.
  • A pkgdown site, R-CMD-check and pkgdown workflows, and a rewritten README.

unexcel 0.1.0

CRAN release: 2025-10-08

First CRAN release.

  • restore_day_month() reverts Excel date serials in a vector to the day.month numerics originally typed, preserving non-serial values.
  • fix_serial_columns() applies the same to the columns of a data frame that look dominated by serials.
  • Both the 1900 and 1904 date systems are supported.