Working on uti and uti_original

This commit is contained in:
Rhet Turnbull
2020-10-03 22:04:35 -07:00
parent d406d30414
commit 1b181094ed
29 changed files with 142 additions and 22 deletions

View File

@@ -1156,7 +1156,13 @@ Returns True if photo is a [cloud asset](#iscloudasset) and is synched to iCloud
**Note**: Applies to master (original) photo only. It's possible for the master to be in iCloud but a local edited version is not yet synched to iCloud. `incloud` provides status of only the master photo. osxphotos does not yet provide a means to determine if the edited version is in iCloud. If you need this feature, please open an [issue](https://github.com/RhetTbull/osxphotos/issues).
#### `uti`
Returns Uniform Type Identifier (UTI) for the image, for example: 'public.jpeg' or 'com.apple.quicktime-movie'
Returns Uniform Type Identifier (UTI) for the current version of the image, for example: 'public.jpeg' or 'com.apple. quicktime-movie'. If the image has been edited, `uti` will return the UTI for the edited image, otherwise it will return the UTI for the original image.
#### `uti_original`
Returns Uniform Type Identifier (UTI) for the original image, for example: 'public.jpeg' or 'com.apple.quicktime-movie'.
#### `uti_raw`
Returns Uniform Type Identifier (UTI) for the associated RAW image, if there is one; for example, 'com.canon.cr2-raw-image'.
#### `burst`
Returns True if photos is a burst image (e.g. part of a set of burst images), otherwise False.

View File

@@ -475,6 +475,13 @@ class PhotoInfo:
"""
return self._info["UTI"]
@property
def uti_original(self):
""" Returns Uniform Type Identifier (UTI) for the original image
for example: public.jpeg or com.apple.quicktime-movie
"""
return self._info["UTI_original"]
@property
def uti_raw(self):
""" Returns Uniform Type Identifier (UTI) for the RAW image if there is one

View File

@@ -989,6 +989,9 @@ class PhotosDB:
self._dbphotos[uuid]["UTI"] = row[22]
# TODO: need to update this for Photos 4
self._dbphotos[uuid]["UTI_original"] = row[22]
# handle burst photos
# if burst photo, determine whether or not it's a selected burst photo
self._dbphotos[uuid]["burstUUID"] = row[23]
@@ -1126,6 +1129,7 @@ class PhotosDB:
info["isMissing"] = row[3]
info["originalFilename"] = row[4]
info["UTI"] = row[5]
info["UTI_original"] = None # filled in later
info["modelID"] = row[6]
info["fileSize"] = row[7]
info["isTrulyRAW"] = row[8]
@@ -2061,14 +2065,19 @@ class PhotosDB:
# determine if a photo is missing in Photos 5
# Get info on remote/local availability for photos in shared albums
# Also get UTI of original image (zdatastoresubtype = 1)
c.execute(
f""" SELECT
{asset_table}.ZUUID,
ZINTERNALRESOURCE.ZLOCALAVAILABILITY,
ZINTERNALRESOURCE.ZREMOTEAVAILABILITY
ZINTERNALRESOURCE.ZREMOTEAVAILABILITY,
ZINTERNALRESOURCE.ZDATASTORESUBTYPE,
ZINTERNALRESOURCE.ZUNIFORMTYPEIDENTIFIER,
ZUNIFORMTYPEIDENTIFIER.ZIDENTIFIER
FROM {asset_table}
JOIN ZADDITIONALASSETATTRIBUTES ON ZADDITIONALASSETATTRIBUTES.ZASSET = {asset_table}.Z_PK
JOIN ZINTERNALRESOURCE ON ZINTERNALRESOURCE.ZASSET = ZADDITIONALASSETATTRIBUTES.ZASSET
JOIN ZUNIFORMTYPEIDENTIFIER ON ZUNIFORMTYPEIDENTIFIER.Z_PK = ZINTERNALRESOURCE.ZUNIFORMTYPEIDENTIFIER
WHERE ZDATASTORESUBTYPE = 1 OR ZDATASTORESUBTYPE = 3 """
)
@@ -2076,8 +2085,11 @@ class PhotosDB:
uuid = row[0]
if uuid in self._dbphotos:
# and self._dbphotos[uuid]["isMissing"] is None:
# logging.warning(f"uuid={uuid}, {row[1]}, {row[2]} {row[3]}")
self._dbphotos[uuid]["localAvailability"] = row[1]
self._dbphotos[uuid]["remoteAvailability"] = row[2]
if row[3] == 1:
self._dbphotos[uuid]["UTI_original"] = row[5]
# old = self._dbphotos[uuid]["isMissing"]
@@ -2104,6 +2116,7 @@ class PhotosDB:
for row in c:
uuid = row[0]
if uuid in self._dbphotos:
# logging.warning(f"uuid={uuid}, {row[1]}, {row[2]}")
self._dbphotos[uuid]["localAvailability"] = row[1]
self._dbphotos[uuid]["remoteAvailability"] = row[2]

View File

@@ -7,7 +7,7 @@
<key>hostuuid</key>
<string>9575E48B-8D5F-5654-ABAC-4431B1167324</string>
<key>pid</key>
<integer>18139</integer>
<integer>2964</integer>
<key>processname</key>
<string>photolibraryd</string>
<key>uid</key>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 336 KiB

After

Width:  |  Height:  |  Size: 338 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 108 KiB

After

Width:  |  Height:  |  Size: 108 KiB

View File

@@ -0,0 +1,68 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>adjustmentBaseVersion</key>
<integer>0</integer>
<key>adjustmentData</key>
<data>
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
rpj9/b9//xc=
</data>
<key>adjustmentEditorBundleID</key>
<string>com.apple.Photos</string>
<key>adjustmentFormatIdentifier</key>
<string>com.apple.photo</string>
<key>adjustmentFormatVersion</key>
<string>1.5</string>
<key>adjustmentTimestamp</key>
<date>2020-10-03T22:54:20Z</date>
</dict>
</plist>

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 MiB

View File

@@ -95,6 +95,19 @@ ALBUM_SORT_ORDER = [
]
ALBUM_KEY_PHOTO = "D79B8D77-BFFC-460B-9312-034F2877D35B"
UTI_DICT = {
"8846E3E6-8AC8-4857-8448-E3D025784410": "public.tiff",
"7783E8E6-9CAC-40F3-BE22-81FB7051C266": "public.jpeg",
"1EB2B765-0765-43BA-A90C-0D0580E6172C": "public.jpeg",
}
UTI_ORIGINAL_DICT = {
"8846E3E6-8AC8-4857-8448-E3D025784410": "public.tiff",
"7783E8E6-9CAC-40F3-BE22-81FB7051C266": "public.heic",
"1EB2B765-0765-43BA-A90C-0D0580E6172C": "public.jpeg",
}
def test_init1():
# test named argument
@@ -1047,7 +1060,7 @@ def test_from_to_date():
photosdb = osxphotos.PhotosDB(PHOTOS_DB)
photos = photosdb.photos(from_date=dt.datetime(2018, 10, 28))
assert len(photos) == 7
assert len(photos) == 7
photos = photosdb.photos(to_date=dt.datetime(2018, 10, 28))
assert len(photos) == 7
@@ -1178,3 +1191,15 @@ def test_import_session_photo():
)
assert len(import_session.photos) == 1
def test_uti():
""" test uti """
import osxphotos
photosdb = osxphotos.PhotosDB(dbfile=PHOTOS_DB)
for uuid, uti in UTI_DICT.items():
photo = photosdb.get_photo(uuid)
assert photo.uti == uti
assert photo.uti_original == UTI_ORIGINAL_DICT[uuid]

View File

@@ -101,6 +101,7 @@ CLI_EXPORT_FILENAMES_CONVERT_TO_JPEG = [
"IMG_1997.JPG",
"IMG_1997.cr2",
"IMG_3092.jpeg",
"IMG_3092_edited.jpeg",
"IMG_4547.jpg",
"Pumkins1.jpg",
"Pumkins2.jpg",
@@ -2894,7 +2895,7 @@ def test_export_touch_files():
)
assert result.exit_code == 0
assert "Exported: 17 photos, touched date: 15 photos" in result.output
assert "Exported: 18 photos, touched date: 16 photos" in result.output
for fname, mtime in zip(CLI_EXPORT_BY_DATE, CLI_EXPORT_BY_DATE_TOUCH_TIMES):
st = os.stat(fname)
@@ -2926,7 +2927,7 @@ def test_export_touch_files_update():
)
assert result.exit_code == 0
assert "Exported: 17 photos" in result.output
assert "Exported: 18 photos" in result.output
assert not pathlib.Path(CLI_EXPORT_BY_DATE[0]).is_file()
@@ -2936,7 +2937,7 @@ def test_export_touch_files_update():
)
assert result.exit_code == 0
assert "Exported: 17 photos" in result.output
assert "Exported: 18 photos" in result.output
assert pathlib.Path(CLI_EXPORT_BY_DATE[0]).is_file()
@@ -2948,7 +2949,7 @@ def test_export_touch_files_update():
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos"
in result.output
)
@@ -2966,7 +2967,7 @@ def test_export_touch_files_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos, touched date: 15 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos, touched date: 16 photos"
in result.output
)
@@ -2989,7 +2990,7 @@ def test_export_touch_files_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos, touched date: 15 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos, touched date: 16 photos"
in result.output
)
@@ -3015,7 +3016,7 @@ def test_export_touch_files_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 1 photo, skipped: 16 photos, updated EXIF data: 0 photos, touched date: 1 photo"
"Exported: 0 photos, updated: 1 photo, skipped: 17 photos, updated EXIF data: 0 photos, touched date: 1 photo"
in result.output
)
@@ -3031,7 +3032,7 @@ def test_export_touch_files_update():
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos"
in result.output
)
@@ -3062,7 +3063,7 @@ def test_export_touch_files_exiftool_update():
)
assert result.exit_code == 0
assert "Exported: 17 photos" in result.output
assert "Exported: 18 photos" in result.output
assert not pathlib.Path(CLI_EXPORT_BY_DATE[0]).is_file()
@@ -3072,7 +3073,7 @@ def test_export_touch_files_exiftool_update():
)
assert result.exit_code == 0
assert "Exported: 17 photos" in result.output
assert "Exported: 18 photos" in result.output
assert pathlib.Path(CLI_EXPORT_BY_DATE[0]).is_file()
@@ -3084,7 +3085,7 @@ def test_export_touch_files_exiftool_update():
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos"
in result.output
)
@@ -3103,7 +3104,7 @@ def test_export_touch_files_exiftool_update():
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 17 photos, skipped: 0 photos, updated EXIF data: 17 photos"
"Exported: 0 photos, updated: 18 photos, skipped: 0 photos, updated EXIF data: 18 photos"
in result.output
)
@@ -3121,7 +3122,7 @@ def test_export_touch_files_exiftool_update():
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 17 photos, skipped: 0 photos, updated EXIF data: 17 photos"
"Exported: 0 photos, updated: 18 photos, skipped: 0 photos, updated EXIF data: 18 photos"
in result.output
)
@@ -3140,7 +3141,7 @@ def test_export_touch_files_exiftool_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos, touched date: 17 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos, touched date: 18 photos"
in result.output
)
@@ -3162,7 +3163,7 @@ def test_export_touch_files_exiftool_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos, touched date: 17 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos, touched date: 18 photos"
in result.output
)
@@ -3187,7 +3188,7 @@ def test_export_touch_files_exiftool_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 1 photo, skipped: 16 photos, updated EXIF data: 1 photo, touched date: 1 photo"
"Exported: 0 photos, updated: 1 photo, skipped: 17 photos, updated EXIF data: 1 photo, touched date: 1 photo"
in result.output
)
@@ -3209,7 +3210,7 @@ def test_export_touch_files_exiftool_update():
)
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos, touched date: 0 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos, touched date: 0 photos"
in result.output
)
@@ -3227,7 +3228,7 @@ def test_export_touch_files_exiftool_update():
assert result.exit_code == 0
assert (
"Exported: 0 photos, updated: 0 photos, skipped: 17 photos, updated EXIF data: 0 photos"
"Exported: 0 photos, updated: 0 photos, skipped: 18 photos, updated EXIF data: 0 photos"
in result.output
)