\startluacode
  documentdata = documentdata or { }
  documentdata.changed = documentdata.changed or { }
  local p = io.popen("ls -l --time-style=long-iso \jobname.tex", "r")
  local time = p:read("*all")
  p:close()

  local P, R, V = lpeg.P, lpeg.R, lpeg.V
  local C, Ct = lpeg.C, lpeg.Ct

  local p_lsout = P{
    [1] = "lsout",
    lsout = V"before" * V"date",
    before = (1 - V"date")^1,
    date  = Ct(C(V"four")
                 * V"hyphen"
                 * C(V"two")
                 * V"hyphen"
                 * C(V"two")
                 * V"space"
                 * Ct(C(V"two")
                        * P":"
                        * C(V"two"))),
    hyphen  = P"-",
    space   = P" ",
    four    = V"digit" * V"digit" * V"digit" * V"digit",
    two     = V"digit" * V"digit",
    digit   = R"09",
  }
  
  local changed = p_lsout:match(time)

  function documentdata.changed.get_changed ()
    if documentdata.changed.__last_changed then
      return documentdata.changed.__last_changed end
    local dateform = {
      changed[3],
      ".",
      changed[2],
      ".",
      changed[1],
      "\\space ",
      changed[4][1],
      ":",
      changed[4][2],
    }
    local datestr = table.concat(dateform)
    documentdata.changed.__last_changed = datestr
    return datestr
  end
\stopluacode

\unexpanded\def\getdate{%
  \ctxlua{context(documentdata.changed.get_changed())}%
}

\starttext

The source of this file was last modified {\os\getdate}.

\stoptext
