[ https://issues.apache.org/jira/browse/COMPRESS-614?focusedWorklogId=752370&page=com.atlassian.jira.plugin.system.issuetabpanels:worklog-tabpanel#worklog-752370 ]
ASF GitHub Bot logged work on COMPRESS-614: ------------------------------------------- Author: ASF GitHub Bot Created on: 04/Apr/22 16:53 Start Date: 04/Apr/22 16:53 Worklog Time Spent: 10m Work Description: garydgregory commented on code in PR #256: URL: https://github.com/apache/commons-compress/pull/256#discussion_r841950804 ########## src/main/java/org/apache/commons/compress/archivers/zip/X000A_NTFS.java: ########## @@ -244,6 +247,36 @@ public Date getCreateJavaTime() { return zipToDate(createTime); } + /** + * Gets the modify time as as a {@link FileTime} + * of this zip entry, or null if no such timestamp exists in the zip entry. + * + * @return modify time as a {@link FileTime} or null. + */ + public FileTime getModifyFileTime() { + return zipToFileTime(modifyTime); + } + + /** + * Gets the access time as a {@link FileTime} + * of this zip entry, or null if no such timestamp exists in the zip entry. + * + * @return access time as a {@link FileTime} or null. + */ + public FileTime getAccessFileTime() { + return zipToFileTime(accessTime); + } + + /** + * Gets the create time as a {@link FileTime} + * of this zip entry, or null if no such timestamp exists in the zip entry. + * + * @return create time as a {@link FileTime} or null. + */ Review Comment: And since tag. ########## src/main/java/org/apache/commons/compress/archivers/zip/X000A_NTFS.java: ########## @@ -304,6 +337,27 @@ public void setCreateTime(final ZipEightByteInteger t) { */ public void setCreateJavaTime(final Date d) { setCreateTime(dateToZip(d)); } + /** + * Sets the modify time. + * + * @param time modify time as a {@link FileTime} + */ + public void setModifyFileTime(final FileTime time) { setModifyTime(fileTimeToZip(time)); } + + /** + * Sets the access time. + * + * @param time access time as a {@link FileTime} + */ Review Comment: And since tag. ########## src/main/java/org/apache/commons/compress/archivers/zip/X000A_NTFS.java: ########## @@ -244,6 +247,36 @@ public Date getCreateJavaTime() { return zipToDate(createTime); } + /** + * Gets the modify time as as a {@link FileTime} + * of this zip entry, or null if no such timestamp exists in the zip entry. + * + * @return modify time as a {@link FileTime} or null. + */ + public FileTime getModifyFileTime() { + return zipToFileTime(modifyTime); + } + + /** + * Gets the access time as a {@link FileTime} + * of this zip entry, or null if no such timestamp exists in the zip entry. + * + * @return access time as a {@link FileTime} or null. + */ + public FileTime getAccessFileTime() { Review Comment: And since tag. ########## src/main/java/org/apache/commons/compress/archivers/zip/X000A_NTFS.java: ########## @@ -244,6 +247,36 @@ public Date getCreateJavaTime() { return zipToDate(createTime); } + /** + * Gets the modify time as as a {@link FileTime} + * of this zip entry, or null if no such timestamp exists in the zip entry. + * + * @return modify time as a {@link FileTime} or null. + */ Review Comment: And since tag. ########## src/main/java/org/apache/commons/compress/archivers/zip/X000A_NTFS.java: ########## @@ -304,6 +337,27 @@ public void setCreateTime(final ZipEightByteInteger t) { */ public void setCreateJavaTime(final Date d) { setCreateTime(dateToZip(d)); } + /** + * Sets the modify time. + * + * @param time modify time as a {@link FileTime} + */ Review Comment: And since tag. ########## src/main/java/org/apache/commons/compress/archivers/zip/X000A_NTFS.java: ########## @@ -304,6 +337,27 @@ public void setCreateTime(final ZipEightByteInteger t) { */ public void setCreateJavaTime(final Date d) { setCreateTime(dateToZip(d)); } + /** + * Sets the modify time. + * + * @param time modify time as a {@link FileTime} + */ + public void setModifyFileTime(final FileTime time) { setModifyTime(fileTimeToZip(time)); } + + /** + * Sets the access time. + * + * @param time access time as a {@link FileTime} + */ + public void setAccessFileTime(final FileTime time) { setAccessTime(fileTimeToZip(time)); } + + /** + * Sets the create time. + * + * @param time create time as a {@link FileTime} + */ + public void setCreateFileTime(final FileTime time) { setCreateTime(fileTimeToZip(time)); } Review Comment: And since tag. Fix formatting. ########## src/test/java/org/apache/commons/compress/utils/TimeUtilsTest.java: ########## @@ -0,0 +1,129 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ +package org.apache.commons.compress.utils; + +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; +import org.junit.jupiter.params.provider.MethodSource; + +import java.nio.file.attribute.FileTime; +import java.time.Instant; +import java.util.Date; +import java.util.stream.Stream; + +import static org.apache.commons.compress.utils.TimeUtils.*; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNull; + +public class TimeUtilsTest { + + public static Stream<Arguments> dateToNtfsProvider() { + return Stream.of( + Arguments.of("1601-01-01T00:00:00.000Z", 0), + Arguments.of("1601-01-01T00:00:00.000Z", 1), + Arguments.of("1600-12-31T23:59:59.999Z", -1), + Arguments.of("1601-01-01T00:00:00.001Z", HUNDRED_NANOS_PER_MILLISECOND), + Arguments.of("1601-01-01T00:00:00.001Z", HUNDRED_NANOS_PER_MILLISECOND + 1), + Arguments.of("1601-01-01T00:00:00.000Z", HUNDRED_NANOS_PER_MILLISECOND - 1), + Arguments.of("1600-12-31T23:59:59.999Z", -HUNDRED_NANOS_PER_MILLISECOND), + Arguments.of("1600-12-31T23:59:59.999Z", -HUNDRED_NANOS_PER_MILLISECOND + 1), + Arguments.of("1600-12-31T23:59:59.998Z", -HUNDRED_NANOS_PER_MILLISECOND - 1), + Arguments.of("1970-01-01T00:00:00.000Z", -WINDOWS_EPOCH_OFFSET), + Arguments.of("1970-01-01T00:00:00.000Z", -WINDOWS_EPOCH_OFFSET + 1), + Arguments.of("1970-01-01T00:00:00.001Z", -WINDOWS_EPOCH_OFFSET + HUNDRED_NANOS_PER_MILLISECOND), + Arguments.of("1969-12-31T23:59:59.999Z", -WINDOWS_EPOCH_OFFSET - 1), + Arguments.of("1969-12-31T23:59:59.999Z", -WINDOWS_EPOCH_OFFSET - HUNDRED_NANOS_PER_MILLISECOND) + ); + } + + public static Stream<Arguments> fileTimeToNtfsProvider() { + return Stream.of( + Arguments.of("1601-01-01T00:00:00.0000000Z", 0), + Arguments.of("1601-01-01T00:00:00.0000001Z", 1), + Arguments.of("1600-12-31T23:59:59.9999999Z", -1), + Arguments.of("1601-01-01T00:00:00.0010000Z", HUNDRED_NANOS_PER_MILLISECOND), + Arguments.of("1601-01-01T00:00:00.0010001Z", HUNDRED_NANOS_PER_MILLISECOND + 1), + Arguments.of("1601-01-01T00:00:00.0009999Z", HUNDRED_NANOS_PER_MILLISECOND - 1), + Arguments.of("1600-12-31T23:59:59.9990000Z", -HUNDRED_NANOS_PER_MILLISECOND), + Arguments.of("1600-12-31T23:59:59.9990001Z", -HUNDRED_NANOS_PER_MILLISECOND + 1), + Arguments.of("1600-12-31T23:59:59.9989999Z", -HUNDRED_NANOS_PER_MILLISECOND - 1), + Arguments.of("1970-01-01T00:00:00.0000000Z", -WINDOWS_EPOCH_OFFSET), + Arguments.of("1970-01-01T00:00:00.0000001Z", -WINDOWS_EPOCH_OFFSET + 1), + Arguments.of("1970-01-01T00:00:00.0010000Z", -WINDOWS_EPOCH_OFFSET + HUNDRED_NANOS_PER_MILLISECOND), + Arguments.of("1969-12-31T23:59:59.9999999Z", -WINDOWS_EPOCH_OFFSET - 1), + Arguments.of("1969-12-31T23:59:59.9990000Z", -WINDOWS_EPOCH_OFFSET - HUNDRED_NANOS_PER_MILLISECOND) + ); + } + + @ParameterizedTest + @MethodSource("dateToNtfsProvider") + public void shouldConvertNtfsTimeToDate(final String instant, final long ntfsTime) { + assertEquals(Instant.parse(instant), ntfsTimeToDate(ntfsTime).toInstant()); + } + + @ParameterizedTest + @MethodSource("dateToNtfsProvider") + public void shouldConvertDateToNtfsTime(final String instant, final long ntfsTime) { + final long ntfsMillis = Math.floorDiv(ntfsTime, HUNDRED_NANOS_PER_MILLISECOND) * HUNDRED_NANOS_PER_MILLISECOND; + final Date parsed = Date.from(Instant.parse(instant)); + assertEquals(ntfsMillis, dateToNtfsTime(parsed)); + } + + @ParameterizedTest + @MethodSource("fileTimeToNtfsProvider") + public void shouldConvertFileTimeToNtfsTime(final String instant, final long ntfsTime) { + final FileTime parsed = FileTime.from(Instant.parse(instant)); + assertEquals(ntfsTime, fileTimeToNtfsTime(parsed)); + } + + @ParameterizedTest + @MethodSource("fileTimeToNtfsProvider") + public void shouldConvertNtfsTimeToFileTime(final String instant, final long ntfsTime) { + final FileTime parsed = FileTime.from(Instant.parse(instant)); + assertEquals(parsed, ntfsTimeToFileTime(ntfsTime)); + } + + @Test + public void shouldConvertNullDateToNullFileTime() { + assertNull(dateToFileTime(null)); + } + + @Test + public void shouldConvertNullFileTimeToNullDate() { + assertNull(fileTimeToDate(null)); + } + + @ParameterizedTest + @MethodSource("dateToNtfsProvider") + public void shouldConvertDateToFileTime(final String instant, final long ignored) { + final Instant parsedInstant = Instant.parse(instant); + final FileTime parsedFileTime = FileTime.from(parsedInstant); + final Date parsedDate = Date.from(parsedInstant); + assertEquals(parsedFileTime, dateToFileTime(parsedDate)); + } + + @ParameterizedTest + @MethodSource("fileTimeToNtfsProvider") + public void shouldConvertFileTimeToDate(final String instant, final long ignored) { + final Instant parsedInstant = Instant.parse(instant); + final FileTime parsedFileTime = FileTime.from(parsedInstant); + final Date parsedDate = Date.from(parsedInstant); + assertEquals(parsedDate, fileTimeToDate(parsedFileTime)); + } +} Review Comment: Add EOL. Issue Time Tracking ------------------- Worklog Id: (was: 752370) Time Spent: 1h 50m (was: 1h 40m) > Use FileTime for time fields in SevenZipArchiveEntry > ---------------------------------------------------- > > Key: COMPRESS-614 > URL: https://issues.apache.org/jira/browse/COMPRESS-614 > Project: Commons Compress > Issue Type: Improvement > Components: Archivers > Affects Versions: 1.21 > Reporter: Andre Brait > Priority: Major > Labels: 7zip > Time Spent: 1h 50m > Remaining Estimate: 0h > > Instead of java.util.Date, which caps precision in milliseconds, let's move > on to using FileTime. > We can keep backwards compatibility through the getters and setters for > modification, access and creation dates. > If you're ok with it, I'll send a PR for this. -- This message was sent by Atlassian Jira (v8.20.1#820001)