Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Image metadata has invalid time offset #4622

Open
Lectem opened this issue Nov 11, 2024 · 5 comments
Open

Image metadata has invalid time offset #4622

Lectem opened this issue Nov 11, 2024 · 5 comments
Labels
bug Something isn't working metadata Related to Exif, XMP, IPTC & Co. needs-analysis Requires further investigation

Comments

@Lectem
Copy link

Lectem commented Nov 11, 2024

1. What is not working as documented?

When analazing my latest photos from Nepal, I'm getting the following error:

metadata: 20241015_095117.heic has invalid time offset +05:45 (exiftool)

The exiftool -j output of one of my photos:

[{
  "SourceFile": "20241015_103317.heic",
  "ExifToolVersion": 12.65,
  "FileName": "20241015_103317.heic",
  "Directory": ".",
  "FileSize": "8.1 MB",
  "FileModifyDate": "2024:10:15 05:49:46+01:00",
  "FileAccessDate": "2024:11:11 11:41:56+01:00",
  "FileInodeChangeDate": "2024:11:11 11:06:51+01:00",
  "FilePermissions": "-rwxrwxrwx",
  "FileType": "HEIC",
  "FileTypeExtension": "heic",
  "MIMEType": "image/heic",
  "MajorBrand": "High Efficiency Image Format HEVC still image (.HEIC)",
  "MinorVersion": "0.0.0",
  "CompatibleBrands": ["mif1","heic"],
  "MediaDataSize": 8112411,
  "MediaDataOffset": 32,
  "HandlerType": "Picture",
  "PrimaryItemReference": 193,
  "MetaImageSize": "8160x6120",
  "ExifByteOrder": "Little-endian (Intel, II)",
  "Make": "samsung",
  "Model": "Galaxy S23",
  "Orientation": "Rotate 90 CW",
  "XResolution": 72,
  "YResolution": 72,
  "ResolutionUnit": "inches",
  "YCbCrPositioning": "Centered",
  "ModifyDate": "2024:10:15 10:33:17",
  "ExposureTime": "1/285",
  "FNumber": 1.8,
  "ExposureProgram": "Program AE",
  "ISO": 25,
  "ExifVersion": "0210",
  "DateTimeOriginal": "2024:10:15 10:33:17",
  "CreateDate": "2024:10:15 10:33:17",
  "OffsetTime": "+05:45",
  "OffsetTimeOriginal": "+05:45",
  "ComponentsConfiguration": "Y, Cb, Cr, -",
  "ApertureValue": 1.8,
  "BrightnessValue": 6.46,
  "ExposureCompensation": 0,
  "MaxApertureValue": 1.8,
  "MeteringMode": "Center-weighted average",
  "Flash": "No Flash",
  "FocalLength": "5.4 mm",
  "SubSecTime": 996,
  "SubSecTimeOriginal": 996,
  "SubSecTimeDigitized": 996,
  "FlashpixVersion": "0100",
  "ColorSpace": "Uncalibrated",
  "ExifImageWidth": 8160,
  "ExifImageHeight": 6120,
  "WhiteBalance": "Auto",
  "DigitalZoomRatio": 1,
  "FocalLengthIn35mmFormat": "23 mm",
  "SceneCaptureType": "Standard",
  "ImageUniqueID": "F50XLPE00PM F50XLPE00PM",
  "HEVCConfigurationVersion": 1,
  "GeneralProfileSpace": "Conforming",
  "GeneralTierFlag": "Main Tier",
  "GeneralProfileIDC": "Main",
  "GenProfileCompatibilityFlags": "Main 10, Main",
  "ConstraintIndicatorFlags": "176 0 0 0 0 0",
  "GeneralLevelIDC": "93 (level 3.1)",
  "MinSpatialSegmentationIDC": 0,
  "ParallelismType": 0,
  "ChromaFormat": "4:2:0",
  "BitDepthLuma": 8,
  "BitDepthChroma": 8,
  "AverageFrameRate": 0,
  "ConstantFrameRate": "Unknown",
  "NumTemporalLayers": 0,
  "TemporalIDNested": "No",
  "ProfileCMMType": "",
  "ProfileVersion": "4.3.0",
  "ProfileClass": "Display Device Profile",
  "ColorSpaceData": "RGB ",
  "ProfileConnectionSpace": "XYZ ",
  "ProfileDateTime": "2022:07:01 00:00:00",
  "ProfileFileSignature": "acsp",
  "PrimaryPlatform": "Unknown (SEC)",
  "CMMFlags": "Not Embedded, Independent",
  "DeviceManufacturer": "Unknown (SEC)",
  "DeviceModel": "",
  "DeviceAttributes": "Reflective, Glossy, Positive, Color",
  "RenderingIntent": "Perceptual",
  "ConnectionSpaceIlluminant": "0.9642 1 0.82491",
  "ProfileCreator": "Unknown (SEC)",
  "ProfileID": 0,
  "ProfileDescription": "DCI-P3 D65 Gamut with sRGB Transfer",
  "ProfileCopyright": "Copyright (c) 2022 Samsung Electronics Co., Ltd.",
  "MediaWhitePoint": "0.9642 1 0.82491",
  "ChromaticAdaptation": "1.04781 0.02289 -0.05013 0.02954 0.99048 -0.01704 -0.00923 0.01505 0.75214",
  "RedMatrixColumn": "0.51508 0.24117 -0.00105",
  "GreenMatrixColumn": "0.29195 0.69223 0.04189",
  "BlueMatrixColumn": "0.15718 0.06659 0.78455",
  "RedTRC": "(Binary data 32 bytes, use -b option to extract)",
  "GreenTRC": "(Binary data 32 bytes, use -b option to extract)",
  "BlueTRC": "(Binary data 32 bytes, use -b option to extract)",
  "ImageWidth": 8160,
  "ImageHeight": 6120,
  "ImageSpatialExtent": "8160x6120",
  "Rotation": 270,
  "TimeStamp": "2024:10:15 05:48:17.996+01:00",
  "Aperture": 1.8,
  "ImageSize": "8160x6120",
  "Megapixels": 49.9,
  "ScaleFactor35efl": 4.3,
  "ShutterSpeed": "1/285",
  "SubSecCreateDate": "2024:10:15 10:33:17.996",
  "SubSecDateTimeOriginal": "2024:10:15 10:33:17.996+05:45",
  "SubSecModifyDate": "2024:10:15 10:33:17.996+05:45",
  "CircleOfConfusion": "0.007 mm",
  "FOV": "76.1 deg",
  "FocalLength35efl": "5.4 mm (35 mm equivalent: 23.0 mm)",
  "HyperfocalDistance": "2.30 m",
  "LightValue": 11.9
}]

OffsetTime is +5:45 which happens to be exactly Nepal's timezone. I don't understand why it's rejected except if the timezones code in Photoprism assumes timezone needs to be exactly 1hour. (yes, anything date/timezone related is complicated, that's why the IANA database exists https://www.iana.org/time-zones )

2. How can we reproduce it?

Steps to reproduce the behavior:

  1. Get a photo with a timezone offset of +5:45
  2. Import it

3. What behavior do you expect?

+5:45 Timezone is accepted.

4. What could be the cause of your problem?

Code not allowing X:30 or X:45 timezones.

5. Can you provide us with example files for testing, error logs, or screenshots?

20241015_103317.zip

6. Which software versions do you use?

(a) PhotoPrism Architecture & Build Number: ARM64, Build [240420-ef5f14bc4]

(b) Database Type & Version: MariaDB

(c) Operating System Types & Versions: Linux

(d) Browser Types & Versions: Firefox

(e) Ad Blockers, Browser Plugins, and/or Firewall Software?

You can find the version/build number of the app in Settings by scrolling to the bottom. Note that MySQL 8 support has been discontinued, see system requirements at https://docs.photoprism.app/getting-started/#system-requirements.

7. On what kind of device is PhotoPrism installed?

(a) Device / Processor Type: NAS, ARM Cortex-A53

(b) Physical Memory & Swap Space in GB: 1GB

(c) Storage Type: HDD

(d) Anything else that might be helpful to know? Nope

@Lectem Lectem added the bug Something isn't working label Nov 11, 2024
@lastzero
Copy link
Member

Thanks for your report! Unfortunately, no one tested and reported this when support for UTC offset "timezones" was added as an alternative to using the official timezone identifier.

The reason fractions are not currently supported is that, based on what was requested at the time of implementation, there is only a fixed set of UTC offsets implemented in the frontend:

export const UtcOffsets = [
{ ID: "UTC-12", Name: "UTC-12:00" },
{ ID: "UTC-11", Name: "UTC-11:00" },
{ ID: "UTC-10", Name: "UTC-10:00" },
{ ID: "UTC-9", Name: "UTC-09:00" },
{ ID: "UTC-8", Name: "UTC-08:00" },
{ ID: "UTC-7", Name: "UTC-07:00" },
{ ID: "UTC-6", Name: "UTC-06:00" },
{ ID: "UTC-5", Name: "UTC-05:00" },
{ ID: "UTC-4", Name: "UTC-04:00" },
{ ID: "UTC-3", Name: "UTC-03:00" },
{ ID: "UTC-2", Name: "UTC-02:00" },
{ ID: "UTC-1", Name: "UTC-01:00" },
{ ID: "UTC", Name: "UTC" },
{ ID: "UTC+1", Name: "UTC+01:00" },
{ ID: "UTC+2", Name: "UTC+02:00" },
{ ID: "UTC+3", Name: "UTC+03:00" },
{ ID: "UTC+4", Name: "UTC+04:00" },
{ ID: "UTC+5", Name: "UTC+05:00" },
{ ID: "UTC+6", Name: "UTC+06:00" },
{ ID: "UTC+7", Name: "UTC+07:00" },
{ ID: "UTC+8", Name: "UTC+08:00" },
{ ID: "UTC+9", Name: "UTC+09:00" },
{ ID: "UTC+10", Name: "UTC+10:00" },
{ ID: "UTC+11", Name: "UTC+11:00" },
{ ID: "UTC+12", Name: "UTC+12:00" },
];

Of course, Asia/Kathmandu is supported as such, i.e. it should be detected automatically if the metadata contains GPS coordinates AND you can select it as timezone in the photo edit dialog:

A possible workaround to avoid this error would be to round the time up or down - but then users will not notice that the chosen UTC offset is not exact. If you're asking for a "quick fix" that can be implemented within the scope of a bug report, that seems feasible. Note that we are currently refactoring the entire frontend codebase, so we cannot implement any changes there in the short term.

@lastzero lastzero added the metadata Related to Exif, XMP, IPTC & Co. label Nov 11, 2024
@Lectem
Copy link
Author

Lectem commented Nov 11, 2024

I'd rather have the "real fix" that supports such timezones properly, I'm not in a hurry !

@lastzero
Copy link
Member

@Lectem I did a little more research on this and found that most timezone databases (lookup tables) don't seem to include an entry for Etc/GMT+05:45 or UTC+05:45:

I'm not an expert on all the timezone implementations out there, so it's unclear what to make of this, i.e. if setting/using/inventing a Etc/GMT+05:45 timezone could cause any follow-up issues (right now, if fails because of our validation, but I'd think other software/operating systems might use similar validation rules unless they can dynamically add zones that are not in the database).

The only explicitly listed zone with a +05:45 offset in common timezone databases seems to be Asia/Kathmandu, as the Etc/GMT zones only exist with full hour offsets.

However, it also does not seem to be 100% correct to (forcefully) map GMT+05:45 to Asia/Kathmandu, although it's probably safe to assume that's the only possibility. Would you consider this a problem?

Note that if you want us to proceed with this request, it would be very helpful if you could help with the research and test what happens with each of the proposed/possible solutions in combination with common tools and operating systems. Thank you very much!

@lastzero lastzero added the needs-analysis Requires further investigation label Feb 24, 2025
@Lectem
Copy link
Author

Lectem commented Feb 24, 2025

Just to make sure I'm understanding things correctly:

  • Front-end only knows about "full hour" time zones
    • Is this only to set values or read them ?
  • Backends prevents conversion during import, but nothing actually stops us to save timezones that are not full hours except the list we use ?
    • } else if utcOffset := txt.UtcOffset(data.TakenAtLocal, data.TakenAt, data.TimeOffset); utcOffset != "" {
    • // Return if time difference includes fractions of an hour.
      if math.Abs(d-float64(int64(d))) > 0.1 {
      return ""
      }
    • At the end of the day, the timezone seems to be computed here:
      func TimeZone(offset string) *time.Location {
      if offset == "" {
      // Local time.
      } else if offset == "UTC" || offset == "Z" {
      return time.UTC
      } else if seconds, err := TimeOffset(offset); err == nil {
      if h := seconds / 3600; h > 0 || h < 0 {
      return time.FixedZone(fmt.Sprintf("UTC%+d", h), seconds)
      }
      } else if zone, zoneErr := time.LoadLocation(offset); zoneErr == nil {
      return zone
      }
      return time.FixedZone("", 0)
      }
      • Which means we could just use the exif TimeOffset field (in the backend), and it will use the following branch
        return time.FixedZone(fmt.Sprintf("UTC%+d", h), seconds)

I think the best way is to not try to guess something impossible to guess. If we get a +05:45 time offset, then just store that and don't try to resolve a "known" timezone.

If the front-end needs to query photos in a specific timezone, let it do it. If for the world map (or any kind of request using timezone), then use a range instead of a hard value (that is, instead of querying UTC+05:00, query the range [UTC+05:00;UTC+06:00[

This way it should also work for other timezones with partial hours (for example https://en.wikipedia.org/wiki/UTC%E2%88%9203:30 https://en.wikipedia.org/wiki/UTC%2B12:45 etc...)

Note that if you want us to proceed with this request, it would be very helpful if you could help with the research and test what happens with each of the proposed/possible solutions in combination with common tools and operating systems. Thank you very much!

I don't mind helping with this, however I do not have a go environment ready, would it require me building the project myself ?

@lastzero
Copy link
Member

lastzero commented Feb 24, 2025

Note that the primary issue is NOT a "list we use", since we don't define what is on the list of common timezones - nor do we control how other apps and tools validate it and what they accept. For example, we also use a JavaScript library that converts timezones (which in turn might let the browser do it, which gets the list from the operating system,...). You could say that we could also customize the browser library to handle this, but what if later we want to write the timezone name back to the original file, or some client (mobile) app gets it from our API and can't handle it? Are you 100% sure that none of this will ever be a problem?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working metadata Related to Exif, XMP, IPTC & Co. needs-analysis Requires further investigation
Projects
None yet
Development

No branches or pull requests

2 participants