mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2024-12-25 15:06:14 +01:00
Merge branch 'fixing_2281' into 'master'
Update GFileInfo to use GDateTime as timestamps Closes #2281 See merge request GNOME/glib!2017
This commit is contained in:
commit
622b31f69e
@ -397,6 +397,8 @@ g_file_info_get_content_type
|
||||
g_file_info_get_size
|
||||
g_file_info_get_modification_time
|
||||
g_file_info_get_modification_date_time
|
||||
g_file_info_get_access_date_time
|
||||
g_file_info_get_creation_date_time
|
||||
g_file_info_get_symlink_target
|
||||
g_file_info_get_etag
|
||||
g_file_info_get_sort_order
|
||||
@ -415,6 +417,8 @@ g_file_info_set_content_type
|
||||
g_file_info_set_size
|
||||
g_file_info_set_modification_time
|
||||
g_file_info_set_modification_date_time
|
||||
g_file_info_set_access_date_time
|
||||
g_file_info_set_creation_date_time
|
||||
g_file_info_set_symlink_target
|
||||
g_file_info_set_sort_order
|
||||
g_file_attribute_matcher_new
|
||||
|
160
gio/gfileinfo.c
160
gio/gfileinfo.c
@ -1834,6 +1834,96 @@ g_file_info_get_modification_date_time (GFileInfo *info)
|
||||
return g_steal_pointer (&dt2);
|
||||
}
|
||||
|
||||
/**
|
||||
* g_file_info_get_access_date_time:
|
||||
* @info: a #GFileInfo.
|
||||
*
|
||||
* Gets the access time of the current @info and returns it as a
|
||||
* #GDateTime.
|
||||
*
|
||||
* This requires the %G_FILE_ATTRIBUTE_TIME_ACCESS attribute. If
|
||||
* %G_FILE_ATTRIBUTE_TIME_ACCESS_USEC is provided, the resulting #GDateTime
|
||||
* will have microsecond precision.
|
||||
*
|
||||
* Returns: (transfer full) (nullable): access time, or %NULL if unknown
|
||||
* Since: 2.70
|
||||
*/
|
||||
GDateTime *
|
||||
g_file_info_get_access_date_time (GFileInfo *info)
|
||||
{
|
||||
static guint32 attr_atime = 0, attr_atime_usec;
|
||||
GFileAttributeValue *value, *value_usec;
|
||||
GDateTime *dt = NULL, *dt2 = NULL;
|
||||
|
||||
g_return_val_if_fail (G_IS_FILE_INFO (info), NULL);
|
||||
|
||||
if (attr_atime == 0)
|
||||
{
|
||||
attr_atime = lookup_attribute (G_FILE_ATTRIBUTE_TIME_ACCESS);
|
||||
attr_atime_usec = lookup_attribute (G_FILE_ATTRIBUTE_TIME_ACCESS_USEC);
|
||||
}
|
||||
|
||||
value = g_file_info_find_value (info, attr_atime);
|
||||
if (value == NULL)
|
||||
return NULL;
|
||||
|
||||
dt = g_date_time_new_from_unix_utc (_g_file_attribute_value_get_uint64 (value));
|
||||
|
||||
value_usec = g_file_info_find_value (info, attr_atime_usec);
|
||||
if (value_usec == NULL)
|
||||
return g_steal_pointer (&dt);
|
||||
|
||||
dt2 = g_date_time_add (dt, _g_file_attribute_value_get_uint32 (value_usec));
|
||||
g_date_time_unref (dt);
|
||||
|
||||
return g_steal_pointer (&dt2);
|
||||
}
|
||||
|
||||
/**
|
||||
* g_file_info_get_creation_date_time:
|
||||
* @info: a #GFileInfo.
|
||||
*
|
||||
* Gets the creation time of the current @info and returns it as a
|
||||
* #GDateTime.
|
||||
*
|
||||
* This requires the %G_FILE_ATTRIBUTE_TIME_CREATED attribute. If
|
||||
* %G_FILE_ATTRIBUTE_TIME_CREATED_USEC is provided, the resulting #GDateTime
|
||||
* will have microsecond precision.
|
||||
*
|
||||
* Returns: (transfer full) (nullable): creation time, or %NULL if unknown
|
||||
* Since: 2.70
|
||||
*/
|
||||
GDateTime *
|
||||
g_file_info_get_creation_date_time (GFileInfo *info)
|
||||
{
|
||||
static guint32 attr_ctime = 0, attr_ctime_usec;
|
||||
GFileAttributeValue *value, *value_usec;
|
||||
GDateTime *dt = NULL, *dt2 = NULL;
|
||||
|
||||
g_return_val_if_fail (G_IS_FILE_INFO (info), NULL);
|
||||
|
||||
if (attr_ctime == 0)
|
||||
{
|
||||
attr_ctime = lookup_attribute (G_FILE_ATTRIBUTE_TIME_CREATED);
|
||||
attr_ctime_usec = lookup_attribute (G_FILE_ATTRIBUTE_TIME_CREATED_USEC);
|
||||
}
|
||||
|
||||
value = g_file_info_find_value (info, attr_ctime);
|
||||
if (value == NULL)
|
||||
return NULL;
|
||||
|
||||
dt = g_date_time_new_from_unix_utc (_g_file_attribute_value_get_uint64 (value));
|
||||
|
||||
value_usec = g_file_info_find_value (info, attr_ctime_usec);
|
||||
if (value_usec == NULL)
|
||||
return g_steal_pointer (&dt);
|
||||
|
||||
dt2 = g_date_time_add (dt, _g_file_attribute_value_get_uint32 (value_usec));
|
||||
g_date_time_unref (dt);
|
||||
|
||||
return g_steal_pointer (&dt2);
|
||||
}
|
||||
|
||||
/**
|
||||
* g_file_info_get_symlink_target:
|
||||
* @info: a #GFileInfo.
|
||||
@ -2237,6 +2327,76 @@ g_file_info_set_modification_date_time (GFileInfo *info,
|
||||
_g_file_attribute_value_set_uint32 (value, g_date_time_get_microsecond (mtime));
|
||||
}
|
||||
|
||||
/**
|
||||
* g_file_info_set_access_date_time:
|
||||
* @info: a #GFileInfo.
|
||||
* @atime: (not nullable): a #GDateTime.
|
||||
*
|
||||
* Sets the %G_FILE_ATTRIBUTE_TIME_ACCESS and
|
||||
* %G_FILE_ATTRIBUTE_TIME_ACCESS_USEC attributes in the file info to the
|
||||
* given date/time value.
|
||||
*
|
||||
* Since: 2.70
|
||||
*/
|
||||
void
|
||||
g_file_info_set_access_date_time (GFileInfo *info,
|
||||
GDateTime *atime)
|
||||
{
|
||||
static guint32 attr_atime = 0, attr_atime_usec;
|
||||
GFileAttributeValue *value;
|
||||
|
||||
g_return_if_fail (G_IS_FILE_INFO (info));
|
||||
g_return_if_fail (atime != NULL);
|
||||
|
||||
if (attr_atime == 0)
|
||||
{
|
||||
attr_atime = lookup_attribute (G_FILE_ATTRIBUTE_TIME_ACCESS);
|
||||
attr_atime_usec = lookup_attribute (G_FILE_ATTRIBUTE_TIME_ACCESS_USEC);
|
||||
}
|
||||
|
||||
value = g_file_info_create_value (info, attr_atime);
|
||||
if (value)
|
||||
_g_file_attribute_value_set_uint64 (value, g_date_time_to_unix (atime));
|
||||
value = g_file_info_create_value (info, attr_atime_usec);
|
||||
if (value)
|
||||
_g_file_attribute_value_set_uint32 (value, g_date_time_get_microsecond (atime));
|
||||
}
|
||||
|
||||
/**
|
||||
* g_file_info_set_creation_date_time:
|
||||
* @info: a #GFileInfo.
|
||||
* @creation_time: (not nullable): a #GDateTime.
|
||||
*
|
||||
* Sets the %G_FILE_ATTRIBUTE_TIME_CREATED and
|
||||
* %G_FILE_ATTRIBUTE_TIME_CREATED_USEC attributes in the file info to the
|
||||
* given date/time value.
|
||||
*
|
||||
* Since: 2.70
|
||||
*/
|
||||
void
|
||||
g_file_info_set_creation_date_time (GFileInfo *info,
|
||||
GDateTime *creation_time)
|
||||
{
|
||||
static guint32 attr_ctime = 0, attr_ctime_usec;
|
||||
GFileAttributeValue *value;
|
||||
|
||||
g_return_if_fail (G_IS_FILE_INFO (info));
|
||||
g_return_if_fail (creation_time != NULL);
|
||||
|
||||
if (attr_ctime == 0)
|
||||
{
|
||||
attr_ctime = lookup_attribute (G_FILE_ATTRIBUTE_TIME_CREATED);
|
||||
attr_ctime_usec = lookup_attribute (G_FILE_ATTRIBUTE_TIME_CREATED_USEC);
|
||||
}
|
||||
|
||||
value = g_file_info_create_value (info, attr_ctime);
|
||||
if (value)
|
||||
_g_file_attribute_value_set_uint64 (value, g_date_time_to_unix (creation_time));
|
||||
value = g_file_info_create_value (info, attr_ctime_usec);
|
||||
if (value)
|
||||
_g_file_attribute_value_set_uint32 (value, g_date_time_get_microsecond (creation_time));
|
||||
}
|
||||
|
||||
/**
|
||||
* g_file_info_set_symlink_target:
|
||||
* @info: a #GFileInfo.
|
||||
|
@ -1057,6 +1057,10 @@ void g_file_info_get_modification_time (GFileInfo *info,
|
||||
G_GNUC_END_IGNORE_DEPRECATIONS
|
||||
GLIB_AVAILABLE_IN_2_62
|
||||
GDateTime * g_file_info_get_modification_date_time (GFileInfo *info);
|
||||
GLIB_AVAILABLE_IN_2_70
|
||||
GDateTime * g_file_info_get_access_date_time (GFileInfo *info);
|
||||
GLIB_AVAILABLE_IN_2_70
|
||||
GDateTime * g_file_info_get_creation_date_time (GFileInfo *info);
|
||||
GLIB_AVAILABLE_IN_ALL
|
||||
const char * g_file_info_get_symlink_target (GFileInfo *info);
|
||||
GLIB_AVAILABLE_IN_ALL
|
||||
@ -1109,6 +1113,12 @@ G_GNUC_END_IGNORE_DEPRECATIONS
|
||||
GLIB_AVAILABLE_IN_2_62
|
||||
void g_file_info_set_modification_date_time (GFileInfo *info,
|
||||
GDateTime *mtime);
|
||||
GLIB_AVAILABLE_IN_2_70
|
||||
void g_file_info_set_access_date_time (GFileInfo *info,
|
||||
GDateTime *atime);
|
||||
GLIB_AVAILABLE_IN_2_70
|
||||
void g_file_info_set_creation_date_time (GFileInfo *info,
|
||||
GDateTime *creation_time);
|
||||
GLIB_AVAILABLE_IN_ALL
|
||||
void g_file_info_set_symlink_target (GFileInfo *info,
|
||||
const char *symlink_target);
|
||||
|
@ -201,6 +201,153 @@ test_g_file_info_modification_time (void)
|
||||
g_date_time_unref (dt_new_usecs);
|
||||
}
|
||||
|
||||
static void
|
||||
test_g_file_info_access_time (void)
|
||||
{
|
||||
GFile *file = NULL;
|
||||
GFileIOStream *io_stream = NULL;
|
||||
GFileInfo *info = NULL;
|
||||
GDateTime *dt = NULL, *dt_usecs = NULL, *dt_new = NULL, *dt_new_usecs = NULL,
|
||||
*dt_before_epoch = NULL, *dt_before_epoch_returned = NULL;
|
||||
GTimeSpan ts;
|
||||
GError *error = NULL;
|
||||
|
||||
g_test_summary ("Test that getting the access time of a file works.");
|
||||
|
||||
file = g_file_new_tmp ("g-file-info-test-XXXXXX", &io_stream, &error);
|
||||
g_assert_no_error (error);
|
||||
|
||||
info = g_file_query_info (file,
|
||||
G_FILE_ATTRIBUTE_TIME_ACCESS,
|
||||
G_FILE_QUERY_INFO_NONE,
|
||||
NULL, &error);
|
||||
g_assert_no_error (error);
|
||||
|
||||
/* Check the access time is retrievable. */
|
||||
dt = g_file_info_get_access_date_time (info);
|
||||
g_assert_nonnull (dt);
|
||||
|
||||
/* Try again with microsecond precision. */
|
||||
g_clear_object (&info);
|
||||
info = g_file_query_info (file,
|
||||
G_FILE_ATTRIBUTE_TIME_ACCESS "," G_FILE_ATTRIBUTE_TIME_ACCESS_USEC,
|
||||
G_FILE_QUERY_INFO_NONE,
|
||||
NULL, &error);
|
||||
g_assert_no_error (error);
|
||||
|
||||
dt_usecs = g_file_info_get_access_date_time (info);
|
||||
g_assert_nonnull (dt_usecs);
|
||||
|
||||
ts = g_date_time_difference (dt_usecs, dt);
|
||||
g_assert_cmpint (ts, >, 0);
|
||||
g_assert_cmpint (ts, <, G_USEC_PER_SEC);
|
||||
|
||||
/* Try round-tripping the access time. */
|
||||
dt_new = g_date_time_add (dt_usecs, G_USEC_PER_SEC + 50);
|
||||
g_file_info_set_access_date_time (info, dt_new);
|
||||
|
||||
dt_new_usecs = g_file_info_get_access_date_time (info);
|
||||
ts = g_date_time_difference (dt_new_usecs, dt_new);
|
||||
g_assert_cmpint (ts, ==, 0);
|
||||
|
||||
// try with a negative timestamp
|
||||
dt_before_epoch = g_date_time_new_from_unix_utc (-10000);
|
||||
g_file_info_set_access_date_time (info, dt_before_epoch);
|
||||
dt_before_epoch_returned = g_file_info_get_access_date_time (info);
|
||||
ts = g_date_time_difference (dt_before_epoch, dt_before_epoch_returned);
|
||||
g_assert_cmpint (ts, ==, 0);
|
||||
|
||||
/* Clean up. */
|
||||
g_clear_object (&io_stream);
|
||||
g_file_delete (file, NULL, NULL);
|
||||
g_clear_object (&file);
|
||||
|
||||
g_clear_object (&info);
|
||||
g_date_time_unref (dt);
|
||||
g_date_time_unref (dt_usecs);
|
||||
g_date_time_unref (dt_new);
|
||||
g_date_time_unref (dt_new_usecs);
|
||||
g_date_time_unref (dt_before_epoch);
|
||||
g_date_time_unref (dt_before_epoch_returned);
|
||||
}
|
||||
|
||||
static void
|
||||
test_g_file_info_creation_time (void)
|
||||
{
|
||||
GFile *file = NULL;
|
||||
GFileIOStream *io_stream = NULL;
|
||||
GFileInfo *info = NULL;
|
||||
GDateTime *dt = NULL, *dt_usecs = NULL, *dt_new = NULL, *dt_new_usecs = NULL,
|
||||
*dt_before_epoch = NULL, *dt_before_epoch_returned = NULL;
|
||||
GTimeSpan ts;
|
||||
GError *error = NULL;
|
||||
|
||||
g_test_summary ("Test that getting the creation time of a file works.");
|
||||
|
||||
file = g_file_new_tmp ("g-file-info-test-XXXXXX", &io_stream, &error);
|
||||
g_assert_no_error (error);
|
||||
|
||||
info = g_file_query_info (file,
|
||||
G_FILE_ATTRIBUTE_TIME_CREATED,
|
||||
G_FILE_QUERY_INFO_NONE,
|
||||
NULL, &error);
|
||||
g_assert_no_error (error);
|
||||
|
||||
/* Check the creation time is retrievable. */
|
||||
dt = g_file_info_get_creation_date_time (info);
|
||||
if (!dt)
|
||||
{
|
||||
g_test_skip ("Skipping testing creation time as it’s not supported by the kernel");
|
||||
g_file_delete (file, NULL, NULL);
|
||||
g_clear_object (&file);
|
||||
g_clear_object (&info);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Try again with microsecond precision. */
|
||||
g_clear_object (&info);
|
||||
info = g_file_query_info (file,
|
||||
G_FILE_ATTRIBUTE_TIME_CREATED "," G_FILE_ATTRIBUTE_TIME_CREATED_USEC,
|
||||
G_FILE_QUERY_INFO_NONE,
|
||||
NULL, &error);
|
||||
g_assert_no_error (error);
|
||||
|
||||
dt_usecs = g_file_info_get_creation_date_time (info);
|
||||
g_assert_nonnull (dt_usecs);
|
||||
|
||||
ts = g_date_time_difference (dt_usecs, dt);
|
||||
g_assert_cmpint (ts, >, 0);
|
||||
g_assert_cmpint (ts, <, G_USEC_PER_SEC);
|
||||
|
||||
/* Try round-tripping the creation time. */
|
||||
dt_new = g_date_time_add (dt_usecs, G_USEC_PER_SEC + 50);
|
||||
g_file_info_set_creation_date_time (info, dt_new);
|
||||
|
||||
dt_new_usecs = g_file_info_get_creation_date_time (info);
|
||||
ts = g_date_time_difference (dt_new_usecs, dt_new);
|
||||
g_assert_cmpint (ts, ==, 0);
|
||||
|
||||
// try with a negative timestamp
|
||||
dt_before_epoch = g_date_time_new_from_unix_utc (-10000);
|
||||
g_file_info_set_creation_date_time (info, dt_before_epoch);
|
||||
dt_before_epoch_returned = g_file_info_get_creation_date_time (info);
|
||||
ts = g_date_time_difference (dt_before_epoch, dt_before_epoch_returned);
|
||||
g_assert_cmpint (ts, ==, 0);
|
||||
|
||||
/* Clean up. */
|
||||
g_clear_object (&io_stream);
|
||||
g_file_delete (file, NULL, NULL);
|
||||
g_clear_object (&file);
|
||||
|
||||
g_clear_object (&info);
|
||||
g_date_time_unref (dt);
|
||||
g_date_time_unref (dt_usecs);
|
||||
g_date_time_unref (dt_new);
|
||||
g_date_time_unref (dt_new_usecs);
|
||||
g_date_time_unref (dt_before_epoch);
|
||||
g_date_time_unref (dt_before_epoch_returned);
|
||||
}
|
||||
|
||||
#ifdef G_OS_WIN32
|
||||
static void
|
||||
test_internal_enhanced_stdio (void)
|
||||
@ -746,6 +893,8 @@ main (int argc,
|
||||
|
||||
g_test_add_func ("/g-file-info/test_g_file_info", test_g_file_info);
|
||||
g_test_add_func ("/g-file-info/test_g_file_info/modification-time", test_g_file_info_modification_time);
|
||||
g_test_add_func ("/g-file-info/test_g_file_info/access-time", test_g_file_info_access_time);
|
||||
g_test_add_func ("/g-file-info/test_g_file_info/creation-time", test_g_file_info_creation_time);
|
||||
#ifdef G_OS_WIN32
|
||||
g_test_add_func ("/g-file-info/internal-enhanced-stdio", test_internal_enhanced_stdio);
|
||||
#endif
|
||||
|
Loading…
Reference in New Issue
Block a user