mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-07-28 11:37:44 +00:00
touch: improve the -d option support of other dates
This commit is contained in:
parent
65d0f5ba9f
commit
06ef89b3d8
2 changed files with 25 additions and 10 deletions
|
@ -16,7 +16,7 @@ use clap::{crate_version, Arg, ArgGroup, Command};
|
|||
use filetime::*;
|
||||
use std::fs::{self, File};
|
||||
use std::path::{Path, PathBuf};
|
||||
use time::macros::{format_description, time};
|
||||
use time::macros::{format_description, offset, time};
|
||||
use time::Duration;
|
||||
use uucore::display::Quotable;
|
||||
use uucore::error::{FromIo, UError, UResult, USimpleError};
|
||||
|
@ -42,6 +42,7 @@ pub mod options {
|
|||
|
||||
static ARG_FILES: &str = "files";
|
||||
|
||||
// Convert a date/time to a date with a TZ offset
|
||||
fn to_local(tm: time::PrimitiveDateTime) -> time::OffsetDateTime {
|
||||
let offset = match time::OffsetDateTime::now_local() {
|
||||
Ok(lo) => lo.offset(),
|
||||
|
@ -52,10 +53,18 @@ fn to_local(tm: time::PrimitiveDateTime) -> time::OffsetDateTime {
|
|||
tm.assume_offset(offset)
|
||||
}
|
||||
|
||||
// Convert a date/time with a TZ offset into a FileTime
|
||||
fn local_dt_to_filetime(dt: time::OffsetDateTime) -> FileTime {
|
||||
FileTime::from_unix_time(dt.unix_timestamp(), dt.nanosecond())
|
||||
}
|
||||
|
||||
// Convert a date/time, considering that the input is in UTC time
|
||||
// Used for touch -d 1970-01-01 18:43:33.023456789 for example
|
||||
fn dt_to_filename(tm: time::PrimitiveDateTime) -> FileTime {
|
||||
let dt = tm.assume_offset(offset!(UTC));
|
||||
local_dt_to_filetime(dt)
|
||||
}
|
||||
|
||||
#[uucore::main]
|
||||
pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||
let matches = uu_app().get_matches_from(args);
|
||||
|
@ -310,15 +319,15 @@ fn parse_date(s: &str) -> UResult<FileTime> {
|
|||
// Tue Dec 3 ...
|
||||
// ("%c", POSIX_LOCALE_FORMAT),
|
||||
//
|
||||
// But also support other format found in the GNU tests like
|
||||
if let Ok(parsed) = time::PrimitiveDateTime::parse(s, &POSIX_LOCALE_FORMAT) {
|
||||
return Ok(local_dt_to_filetime(to_local(parsed)));
|
||||
}
|
||||
|
||||
// Also support other formats found in the GNU tests like
|
||||
// in tests/misc/stat-nanoseconds.sh
|
||||
for fmt in [
|
||||
POSIX_LOCALE_FORMAT,
|
||||
YYYYMMDDHHMMS_FORMAT,
|
||||
YYYYMMDDHHMMSS_FORMAT,
|
||||
] {
|
||||
for fmt in [YYYYMMDDHHMMS_FORMAT, YYYYMMDDHHMMSS_FORMAT] {
|
||||
if let Ok(parsed) = time::PrimitiveDateTime::parse(s, &fmt) {
|
||||
return Ok(local_dt_to_filetime(to_local(parsed)));
|
||||
return Ok(dt_to_filename(parsed));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -438,7 +438,7 @@ fn test_touch_set_date4() {
|
|||
|
||||
assert!(at.file_exists(file));
|
||||
|
||||
let expected = FileTime::from_unix_time(60213, 0);
|
||||
let expected = FileTime::from_unix_time(67413, 0);
|
||||
let (atime, mtime) = get_file_times(&at, file);
|
||||
assert_eq!(atime, mtime);
|
||||
assert_eq!(atime, expected);
|
||||
|
@ -456,7 +456,13 @@ fn test_touch_set_date5() {
|
|||
|
||||
assert!(at.file_exists(file));
|
||||
|
||||
let expected = FileTime::from_unix_time(60213, 023456789);
|
||||
// Slightly different result on Windows for nano seconds
|
||||
// TODO: investigate
|
||||
#[cfg(windows)]
|
||||
let expected = FileTime::from_unix_time(67413, 23456700);
|
||||
#[cfg(not(windows))]
|
||||
let expected = FileTime::from_unix_time(67413, 23456789);
|
||||
|
||||
let (atime, mtime) = get_file_times(&at, file);
|
||||
assert_eq!(atime, mtime);
|
||||
assert_eq!(atime, expected);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue