2011-12-08 30 views
8

Tôi đang cố gắng đặt thời gian tạo hệ thống tập tin cho một tệp trên Mac OS bằng tập lệnh ruby.Làm cách nào để đặt thời gian tạo tệp bằng ruby ​​trên Mac OS?

Trên Mac OS X 'ctime' đại diện cho lần sửa đổi inode cuối cùng thay vì thời gian tạo tệp, do đó, sử dụng File.utime() của ruby ​​để đặt thời gian sẽ không trợ giúp.

Sử dụng gợi ý này [http://inessential.com/2008/12/18/file_creation_date_in_ruby_on_macs] Tôi có thể lấy thời gian tạo một file:

Time.parse(`mdls -name kMDItemContentCreationDate -raw "#{filename}"`) 

... nhưng bất kỳ ý tưởng về làm thế nào để cài đặt nó sử dụng ruby?

- CẬP NHẬT -

Được rồi, tôi nghĩ tôi có thể thực sự làm điều này với File.utime trong ruby.

Mặc dù ctime được về mặt kỹ thuật không được sử dụng bởi Mac OS để theo dõi thời gian tạo tập tin, khi bạn sử dụng utime để cập nhật các ctime (cùng với mtime, mà phải được đồng thời thiết lập) hệ thống tập tin dường như kỳ diệu cũng cập nhật thời gian tạo theo kMDItemContentCreationDate.

Vì vậy, để thiết lập filename đến một ctime của ngày 01 tháng 10 2010 và một mtime của ngày 02 tháng 10 2010:

File.utime(Time.strptime('011010', '%d%m%y'), Time.strptime('021010', '%d%m%y'), filename) 
+1

bạn có thể muốn đăng 'cập nhật' giải pháp của mình làm câu trả lời, vì vậy câu hỏi này không cần phải mở (và 'chưa trả lời') – robustus

+0

Bạn hiểu điều này không phải là di động. Linux không hỗ trợ lưu trữ thời gian tạo. Ngoài ra ctime không phải là thời gian tạo, nó là "thay đổi" thời gian theo thư mục, không phải cho chính tệp đó. Điều này có thể giải thích: http://stackoverflow.com/a/4009369/128421 –

+1

Đặt thời gian tệp bằng cách sử dụng 'utime' KHÔNG thay đổi giá trị được trả về bằng cách sử dụng' mdls -name kMDItemContentCreationDate -raw'. –

Trả lời

11

Có một giải pháp Ruby với phương pháp utime. Nhưng bạn sẽ phải đặt thời gian sửa đổi (mtime) và thời gian truy cập (atime) cùng một lúc. Nếu bạn muốn giữ thời gian truy cập, bạn có thể sử dụng:

File.utime(File.atime(path), modification_time, path) 

Xem Ruby core documentation.

+3

Điều này không cập nhật ngày tạo –

+0

Nếu bạn chạy 'stat -s' trên tệp đó, bạn sẽ thấy rằng điều này không cập nhật thuộc tính' st_ctime'. – fotinakis

3

Vì vậy, bạn đã chắc chắn có một tinh khiết của Ruby giải pháp làm việc, nhưng vì đây là OS X , bạn có phản đối exec() hoặc system() và chỉ sử dụng touch? Trong trường hợp của bạn, tôi gần như muốn:

system "touch -t YYYYMMDDhhmm /what/ever" 

nếu không có lý do nào khác hơn là rõ ràng.

+0

'touch' không sử dụng cùng một cơ chế mà' mdls -name kMDItemContentCreationDate -raw' thực hiện. –

1

này làm việc cho tôi để cập nhật thời gian tạo trên OS X 10.11.1:

system "SetFile -d '#{time.strftime "%m/%d/%Y %H:%M:%S"}' #{file}" 

Không tuyên bố của tính di động - SetFile là một lệnh OS X (và man page nói nó bị phản đối với XCode 6, vì vậy có thể không hoạt động trong thời gian dài) - không thể tìm cách khác để thực hiện điều đó, Time.utime không cập nhật thời gian tạo mà chỉ thời gian được sửa đổi và truy cập.

Xem: https://apple.stackexchange.com/q/99536/65787

0

Ruby sử dụng các cuộc gọi hệ thống utimes để thay đổi tập tin lần.

Đọc man-page cho utimes giải thích những gì sẽ xảy ra:

int utimes (const char * path, const struct timeval * lần); .. Nếu thời gian không phải là NULL, nó được giả định trỏ đến một mảng của hai cấu trúc thời gian . Thời gian truy cập được đặt thành giá trị của phần tử đầu tiên, và thời gian sửa đổi được đặt thành giá trị của phần tử thứ hai. Đối với các hệ thống tệp hỗ trợ thời gian tạo tệp (tạo) (chẳng hạn như UFS2), thời gian sinh sẽ được đặt thành giá trị của phần tử thứ hai nếu phần tử thứ hai lớn hơn thời gian sinh được đặt hiện tại. Để đặt cả thời gian sinh và thời gian sửa đổi, cần có hai cuộc gọi; người đầu tiên đặt thời gian sinh và lần thứ hai để đặt thời gian sửa đổi (có lẽ mới hơn) . ...

Vì vậy, giờ chỉ được cập nhật ngược thời gian.

Các vấn đề liên quan