ExifTool Forum

ExifTool => Newbies => Topic started by: boomaka on June 29, 2022, 08:48:46 PM

Title: Conditionally updating UTC Offset based on GPSDateTime
Post by: boomaka on June 29, 2022, 08:48:46 PM
Hi all,

After scouring posts it's clear DST causes issues for many USians...I'm working on cleaning up multitudes of files, and thought it would be a good idea to use the GPSDateTime composite tag, converting to the local timezone as needed.

It's twice as inefficient, but I thought an effective way to go about it would be to check if GPSDateTime is (for example) >=2007-03-13 02:00 or < 2007-11-04 02:00. Unfortunately, I think I need to "state" the GPSDateTime differently in order for it to be properly parsed, as I'm able to consistently set the wrong timezone when it should fail the check. As an aside, I wonder if I could build a file containing DST dates and reference that automatically... Anyway, here's what I'm doing:

This image has a few tags, locally-set to UTC-4:
exiftool -G1 -s -alldates -XMP:DateTimeOriginal -GPSDateTime -XMP:CreateDate 'IMG_20171001_130637.jpg'
[ExifIFD]       DateTimeOriginal                : 2017:10:01 13:06:37
[ExifIFD]       CreateDate                      : 2017:10:01 13:06:37
[IFD0]          ModifyDate                      : 2017:10:01 13:06:37
[Composite]     GPSDateTime                     : 2017:10:01 17:06:30Z



I want to shift the dates by -5 or -4 depending on whether the time falls within DST. I actually got different results using lt/ge and < / >= with it either failing or (more often) passing the check as I change the reference style, regardless of whether it falls in the stated date range. I tried specifying $GPSDateTime as $GPSDateTime, ${GPSDateTime}, and ${GPSDateTime;DateFmt('%Y%m%d%H')}.  In none of them was I able to get the image to fail one check but pass the other.

I think I need to step away for a few hours and come back to this, but I'll share one series of attempts using the ${GPSDateTime} approach to save extra reading:

time exiftool -r -m -v0 '-alldates<${GPSDateTime}-5:00' '-DateTimeOriginal<${GPSDateTime}-05:00' '-XMP:CreateDate<${GPSDateTime}-05:00' '-XMP:DateTimeOriginal<${GPSDateTime}-05:00' -globaltimeshift -5 -if '${GPSDateTime} lt '2017031102' or ${GPSDateTime} gt '2017110402'' 'IMG_20171001_130637.jpg'
 
======== IMG_20171001_130637.jpg
Warning: Error rebuilding maker notes (may be corrupt) - IMG_20171001_130637.jpg
    1 image files updated


Dates were added and all shifted by -5, although I'd expect this check to fail because 10/1 is within DST:

exiftool -G1 -s -alldates -XMP:DateTimeOriginal -GPSDateTime -XMP:CreateDate 'IMG_20171001_130637.jpg'
[ExifIFD]       DateTimeOriginal                : 2017:10:01 12:06:30
[ExifIFD]       CreateDate                      : 2017:10:01 12:06:30
[IFD0]          ModifyDate                      : 2017:10:01 12:06:30
[XMP-exif]      DateTimeOriginal                : 2017:10:01 12:06:30-05:00
[Composite]     GPSDateTime                     : 2017:10:01 17:06:30Z
[XMP-xmp]       CreateDate                      : 2017:10:01 12:06:30-05:00


Likewise, I'll run the counterpart command that shifts to UTC-4 if the range is within the DST timeframe (which it should pass anyway):


time exiftool -r -m -v0 '-alldates<${GPSDateTime}-4:00' '-DateTimeOriginal<${GPSDateTime}-4:00' '-XMP:CreateDate<${GPSDateTime}-4:00' '-XMP:DateTimeOriginal<${GPSDateTime}-4:00' -globaltimeshift -4 -if '${GPSDateTime} ge '2017031102' or ${GPSDateTime} lt '2017110402'' 'IMG_20171001_130637.jpg'
======== IMG_20171001_130637.jpg
Warning: Error rebuilding maker notes (may be corrupt) - IMG_20171001_130637.jpg
    1 image files updated

exiftool -G1 -s -alldates -XMP:DateTimeOriginal -GPSDateTime -XMP:CreateDate 'IMG_20171001_130637.jpg'
[ExifIFD]       DateTimeOriginal                : 2017:10:01 13:06:30
[ExifIFD]       CreateDate                      : 2017:10:01 13:06:30
[IFD0]          ModifyDate                      : 2017:10:01 13:06:30
[XMP-exif]      DateTimeOriginal                : 2017:10:01 13:06:30-04:00
[Composite]     GPSDateTime                     : 2017:10:01 17:06:30Z
[XMP-xmp]       CreateDate                      : 2017:10:01 13:06:30-04:00


This last one is setting to UTC-4, but since it's from 12/25 it should fail:

exiftool -G1 -s -alldates -XMP:DateTimeOriginal -GPSDateTime -XMP:CreateDate 'IMG_20171225_145355.jpg'
[ExifIFD]       DateTimeOriginal                : 2017:12:25 14:53:55
[ExifIFD]       CreateDate                      : 2017:12:25 14:53:55
[IFD0]          ModifyDate                      : 2017:12:25 14:53:55
[Composite]     GPSDateTime                     : 2017:12:25 19:53:46Z

time exiftool -r -m -v0 '-alldates<${GPSDateTime}-4:00' '-DateTimeOriginal<${GPSDateTime}-4:00' '-XMP:CreateDate<${GPSDateTime}-4:00' '-XMP:DateTimeOriginal<${GPSDateTime}-4:00' -globaltimeshift -4 -if '${GPSDateTime} ge '2017031102' or ${GPSDateTime} lt '2017110402'' 'IMG_20171225_145355.jpg'
======== IMG_20171225_145355.jpg
Warning: Error rebuilding maker notes (may be corrupt) - IMG_20171225_145355.jpg
    1 image files updated


exiftool -G1 -s -alldates -XMP:DateTimeOriginal -GPSDateTime -XMP:CreateDate 'IMG_20171225_145355.jpg'
exiftool -G1 -s -alldates -XMP:DateTimeOriginal -GPSDateTime -XMP:CreateDate 'IMG_20171225_145355.jpg'
[ExifIFD]       DateTimeOriginal                : 2017:12:25 15:53:46
[ExifIFD]       CreateDate                      : 2017:12:25 15:53:46
[IFD0]          ModifyDate                      : 2017:12:25 15:53:46
[XMP-exif]      DateTimeOriginal                : 2017:12:25 15:53:46-04:00
[Composite]     GPSDateTime                     : 2017:12:25 19:53:46Z
[XMP-xmp]       CreateDate                      : 2017:12:25 15:53:46-04:00



I'm positive I'm missing something super silly.
Title: Re: Conditionally updating UTC Offset based on GPSDateTime
Post by: StarGeek on June 29, 2022, 11:04:31 PM
If your computer is in the same time zone as where the picture was taken, then the easiest thing to do is let the computer figure it out.  Just copy the time stamp from the file into FileModifyDate and/or FileCreateDate.  The computer already knows if the date was Daylight savings or not.

For example, I'm in Pacific time.  This example has the DateTimeOriginal set to today, Daylight savings, and the CreateDate set to January 1, Standard time.  I'll copy these tags to the file system tags and the results will have the correct time zones
C:\>exiftool -time:all -G -a -s y:\!temp\Test4.jpg
[File]          FileModifyDate                  : 2020:07:11 01:23:10-07:00
[File]          FileAccessDate                  : 2022:06:29 19:28:04-07:00
[File]          FileCreateDate                  : 2021:09:07 07:41:30-07:00
[EXIF]          DateTimeOriginal                : 2022:06:29 12:00:00
[EXIF]          CreateDate                      : 2022:01:01 12:00:00

C:\>exiftool "-FileCreateDate<CreateDate" "-FileModifyDate<DateTimeOriginal" y:\!temp\Test4.jpg
    1 image files updated

C:\>exiftool -time:all -G -a -s y:\!temp\Test4.jpg
[File]          FileModifyDate                  : 2022:06:29 12:00:00-07:00
[File]          FileAccessDate                  : 2022:06:29 12:00:00-07:00
[File]          FileCreateDate                  : 2022:01:01 12:00:00-08:00
[EXIF]          DateTimeOriginal                : 2022:06:29 12:00:00
[EXIF]          CreateDate                      : 2022:01:01 12:00:00


From there, you can copy these tags into any other tag.  If you copy these tags into the GPS time stamps, exiftool will automatically adjust to UTC.
C:\>exiftool -P -overwrite_original "-GPS*Stamp<FileModifyDate" y:\!temp\Test4.jpg
    1 image files updated

C:\>exiftool -time:all -G -a -s y:\!temp\Test4.jpg
[File]          FileModifyDate                  : 2022:06:29 12:00:00-07:00
[File]          FileAccessDate                  : 2022:06:29 19:33:21-07:00
[File]          FileCreateDate                  : 2022:01:01 12:00:00-08:00
[EXIF]          DateTimeOriginal                : 2022:06:29 12:00:00
[EXIF]          CreateDate                      : 2022:01:01 12:00:00
[EXIF]          GPSTimeStamp                    : 19:00:00
[EXIF]          GPSDateStamp                    : 2022:06:29
[Composite]     GPSDateTime                     : 2022:06:29 19:00:00Z


If you want to copy to the GPS time stamps, I suggest copying to GPSTimeStamp and GPSDateStamp.  These are the standard tags that most programs will read.  In this example, I'm using a wildcard to copy to both tags in a single call.

Your examples are copying to GPSDateTime but the thing you're not catching is the exact location you're copying to.  Because you don't have the -a (-duplicates) option (https://exiftool.org/exiftool_pod.html#a---a--duplicates---duplicates) set, all you see is the Composite:GPSDateTime, which is not actually embedded in the file (see the Composite tags page (https://exiftool.org/TagNames/Composite.html)).  The tag you are actually copying to is the XMP:GPSDateTime tag.  See FAQ #3 (https://exiftool.org/faq.html#Q3).
C:\>exiftool -P -overwrite_original "-GPSDateTime<FileModifyDate" y:\!temp\Test4.jpg
    1 image files updated

C:\>exiftool -time:all -G -a -s y:\!temp\Test4.jpg
[File]          FileModifyDate                  : 2022:06:29 12:00:00-07:00
[File]          FileAccessDate                  : 2022:06:29 19:35:45-07:00
[File]          FileCreateDate                  : 2022:01:01 12:00:00-08:00
[EXIF]          DateTimeOriginal                : 2022:06:29 12:00:00
[EXIF]          CreateDate                      : 2022:01:01 12:00:00
[XMP]           GPSDateTime                     : 2022:06:29 12:00:00-07:00


You should also take note that the tags covered by Alldates, the EXIF:CreateDate, EXIF:ModifyDate, and EXIF:DateTimeOriginal, do not include a time zone component, so there's no purpose copying time zones to them.  Instead, the time zones are held in separate tags, EXIF:OffsetTimeDigitized, EXIF:OffsetTime, and EXIF:OffsetTimeOriginal respectively. You can also use a wildcard in this case as well
C:\>exiftool -P -overwrite_original "-OffsetTime*<FileModifyDate" y:\!temp\Test4.jpg
    1 image files updated

C:\>exiftool -time:all -G -a -s y:\!temp\Test4.jpg
[File]          FileModifyDate                  : 2022:06:29 12:00:00-07:00
[File]          FileAccessDate                  : 2022:06:29 19:53:56-07:00
[File]          FileCreateDate                  : 2022:01:01 12:00:00-08:00
[EXIF]          DateTimeOriginal                : 2022:06:29 12:00:00
[EXIF]          CreateDate                      : 2022:01:01 12:00:00
[EXIF]          OffsetTime                      : -07:00
[EXIF]          OffsetTimeOriginal              : -07:00
[EXIF]          OffsetTimeDigitized             : -07:00
[Composite]     SubSecCreateDate                : 2022:01:01 12:00:00-07:00
[Composite]     SubSecDateTimeOriginal          : 2022:06:29 12:00:00-07:00


As I stated at the beginning, this all assumes that the computer is in the same time zone as where the images were taken, irrespective of Daylight savings.  Offhand, I can't think of a real easy way to set the time zone properly and automatically.  You could set the system time stamps as above and take note of those values if it's Daylight time or not, and then adjust things manually.
Title: Re: Conditionally updating UTC Offset based on GPSDateTime
Post by: boomaka on June 30, 2022, 08:23:07 AM
First, thank you for the additional guidance; it's sent me even further down the exiftool rabbit hole. A week ago I learned about exiftool and have been learning it as I go to tag, rename, and organize ~40K photos, discovering all kinds of new edge cases lol. The wall of text below is a bit OT but might provide some context into where I'm coming from. To respond directly some of your comments about GPSDateTime, though, and make sure I understood you:

     exiftool -r -m -v0 '-alldates<${GPSDateTime}' '-XMP:CreateDate<${GPSDateTime}-4:00' '-XMP:DateTimeOriginal<${GPSDateTime}-4:00'
     
That last point highlights my misunderstanding; I was under the impression that since it concatenates GPSDateStamp and GPSTimeStamp, updates to it would be split across those two tags, which doesn't appear to be the case.
That last point highlights my misunderstanding; I was under the impression that since it concatenates GPSDateStamp and GPSTimeStamp, updates to it would be split across those two tags, which doesn't appear to be the case.

Thank you again.



I didn't think my photos consistently had a DateTimeOriginal set (which, strictly speaking would be EXIF:DateTimeOriginal, right?), at least based on what Windows shows for Date Taken. The -5 was a misunderstanding on my part though that it would also shift that specific time value, although it'd be redundant with -globaltimeshift. FWIW, I'm running the tool in a terminal on my server but using the Explorer GUI to quickly see how that field updates and which images are renamed with null values where DateTimeOriginal would be used. Before getting to this point, I was using DateTimeOriginal and ended up with a few dozen files that went from Image.jpg to - Image.jpg instead of 20100101 - Image.jpg.

For each given year, I need to do some more analysis to determine whether DateTimeOriginal is there before doing anything else since Windows Explorer doesn't seem to be the most...accurate all the time. I can't go through the entire library without accounting for a variety of edge cases in any given year:

Not being totally confident in the state of the tags, GPSDateTime seemed to be the most consistently populated to make sure that all of the photos had relatively consistent EXIF and XMP values so I can re-up them into Google Photos, since editing the dates in Photos doesn't actually update the file. What I might try then is physically moving the images to a few directories based on which tags are populated and go from there.

All this to say: Thank you again for the additional guidance, and it's sent me further down the rabbit hole  ;D
Title: Re: Conditionally updating UTC Offset based on GPSDateTime
Post by: StarGeek on June 30, 2022, 11:27:26 AM
Quote from: boomaka on June 30, 2022, 08:23:07 AM
I thought I'm copying from GPSDateTime, no? i.e., '-XMP:DateTimeOriginal<${GPSDateTime}-05:00'

My mistake.  Yes, you are correct.  There was a lot to go through and I jumped to a conclusion, as I am apt to do.

QuoteI see that I have some redundant references, and could clean things up a bit to (roughly)[/li][/list]
exiftool -r -m -v0 '-alldates<${GPSDateTime}' '-XMP:CreateDate<${GPSDateTime}-4:00' '-XMP:DateTimeOriginal<${GPSDateTime}-4:00'

I would also add in XMP:DateCreated, as that is what is called for by the IPTC Photo Metadata Standard (https://www.iptc.org/std/photometadata/specification/IPTC-PhotoMetadata).  You can change the command as follows.  This will write the correct EXIF and IPTC standard timestamps, as well as XMP:DateTimeOriginal, which isn't actually part of the current standards.  The DateCreated is the corresponding tag.
exiftool -r -m -v0 '-alldates<${GPSDateTime}' '-XMP:alldates<${GPSDateTime}' '-XMP:DateCreated<${GPSDateTime}-4:00'

QuoteThe 3 EXIF offset tags you mentioned are specifically used by each respective tag?
  • EXIF:OffsetTimeOriginal ... EXIF:DateTimeOriginal
  • EXIF:OffsetTime ... EXIF:ModifyDate
  • EXIF:OffsetTimeDigitized ... EXIF:CreateDate

Yes, that is correct.

QuoteGPSDateTime as a composite is strictly-speaking, XMP:GPSDateTime?

No, they are two separate tags.  XMP:GPSDateTime is an embedded tag.  Composite tags, such as Composite:GPSDateTime, are tags that exiftool creates by combining other tags after reading all the data in the file.  They are mostly used to copy to other tags as a convenience or to be easier to read.  In this case, GPS time stamps are split into two separate tags (as are most of the EXIF based GPS tags). The Composite tag combines them to be easier to read and copy to other tags, as you are doing.

The XMP:GPSDateStamp (specifically it's XMP-Exif:GPSDateStamp) is a tag that is part of the EXIF for XMP standard, and would be used in XMP sidecar files.  As a tangent, the tag is actually called GPSTimeStamp by the specs but exiftool renames it as to prevent the error of copying from the EXIF:GPSTimeStamp, which would not include the date.

QuoteThat last point highlights my misunderstanding; I was under the impression that since it concatenates GPSDateStamp and GPSTimeStamp, updates to it would be split across those two tags, which doesn't appear to be the case.

No.  While some can be written to and will update more than one tag at a time, most Composite tags are not writable.  This is one of those.  See the Composte tags page linked above.

Three useful writable Composite tags are SubSecCreateDate, SubSecDateTimeOriginal, and SubSecModifyDate, which will write to the appropriate EXIF time stamp and their related subsecond and offset time tags at once.

QuoteI didn't think my photos consistently had a DateTimeOriginal set (which, strictly speaking would be EXIF:DateTimeOriginal, right?)

Yes, though you don't need to specify the EXIF part, as by default exiftool will prefer to write to EXIF tags.  You would only need to specify XMP if you wanted to write to XMP:DateTimeOriginal

Quoteat least based on what Windows shows for Date Taken.

You can look at this post (https://exiftool.org/forum/index.php?topic=6591.msg32875#msg32875) to see what tags Windows will actually read/write to fill the "Date Taken" property, as there are multiple possible tags.

QuoteI was using DateTimeOriginal and ended up with a few dozen files that went from Image.jpg to - Image.jpg instead of 20100101 - Image.jpg.

Note #1 under the -TAG[+-^]=[VALUE] option (https://exiftool.org/exiftool_pod.html#TAG---VALUE) is useful here.  You can add a fallback rename in such cases that are missing the DateTimeOriginal tag.
exiftool -d '%Y%m%d - %%f.%%e' '-Filename=No Date - %f.%e' '-Filename<DateTimeOriginal' /path/to/files/
Title: Re: Conditionally updating UTC Offset based on GPSDateTime
Post by: boomaka on June 30, 2022, 02:50:07 PM
You're an absolute fountain of knowledge; thanks for taking the time to unpack my story :). I'll incorporate those recommendations and see how I make out.