Added tests, fixed bug in export_db

This commit is contained in:
Rhet Turnbull
2020-10-03 11:58:48 -07:00
parent 15eb940ff0
commit 5a13605f85
10 changed files with 262 additions and 49 deletions

View File

@@ -1236,6 +1236,15 @@ def query(
help="Convert all non-jpeg images (e.g. RAW, HEIC, PNG, etc) "
"to JPEG upon export.",
)
@click.option(
"--jpeg-quality",
type=click.FloatRange(0.0, 1.0),
default=1.0,
help="Value in range 0.0 to 1.0 to use with --convert-to-jpeg. "
"A value of 1.0 specifies best quality, "
"a value of 0.0 specifies maximum compression. "
"Defaults to 1.0."
)
@click.option(
"--sidecar",
default=None,
@@ -1356,6 +1365,7 @@ def export(
description_template,
current_name,
convert_to_jpeg,
jpeg_quality,
sidecar,
only_photos,
only_movies,
@@ -1628,6 +1638,7 @@ def export(
edited_suffix=edited_suffix,
use_photos_export=use_photos_export,
convert_to_jpeg=convert_to_jpeg,
jpeg_quality=jpeg_quality,
)
results_exported.extend(results.exported)
results_new.extend(results.new)
@@ -1676,6 +1687,7 @@ def export(
edited_suffix=edited_suffix,
use_photos_export=use_photos_export,
convert_to_jpeg=convert_to_jpeg,
jpeg_quality=jpeg_quality,
)
results_exported.extend(results.exported)
results_new.extend(results.new)
@@ -2167,6 +2179,7 @@ def export_photo(
edited_suffix="_edited",
use_photos_export=False,
convert_to_jpeg=False,
jpeg_quality=1.0,
):
""" Helper function for export that does the actual export
@@ -2199,6 +2212,7 @@ def export_photo(
touch_file: boolean; sets file's modification time to match photo date
use_photos_export: boolean; if True forces the use of AppleScript to export even if photo not missing
convert_to_jpeg: boolean; if True, converts non-jpeg images to jpeg
jpeg_quality: float in range 0.0 <= jpeg_quality <= 1.0. A value of 1.0 specifies use best quality, a value of 0.0 specifies use maximum compression.
Returns:
list of path(s) of exported photo or None if photo was missing
@@ -2286,6 +2300,7 @@ def export_photo(
dry_run=dry_run,
touch_file=touch_file,
convert_to_jpeg=convert_to_jpeg,
jpeg_quality=jpeg_quality,
)
results_exported.extend(export_results.exported)
@@ -2346,6 +2361,7 @@ def export_photo(
dry_run=dry_run,
touch_file=touch_file,
convert_to_jpeg=convert_to_jpeg,
jpeg_quality=jpeg_quality,
)
results_exported.extend(export_results_edited.exported)

View File

@@ -94,6 +94,11 @@ class ExportDB_ABC(ABC):
class ExportDBNoOp(ExportDB_ABC):
""" An ExportDB with NoOp methods """
def __init__(self):
self.was_created = True
self.was_upgraded = False
self.version = OSXPHOTOS_EXPORTDB_VERSION
def get_uuid_for_file(self, filename):
pass
@@ -441,36 +446,27 @@ class ExportDB(ExportDB_ABC):
raise ValueError(f"expected 3 elements for stat, got {len(stats)}")
conn = self._conn
try:
c = conn.cursor()
c.execute(
f"UPDATE {table} "
+ "SET converted_mode = ?, converted_size = ?, converted_mtime = ? "
+ "WHERE filepath_normalized = ?;",
(*stats, filename),
)
conn.commit()
except Error as e:
logging.warning(e)
c = conn.cursor()
c.execute(
f"INSERT OR REPLACE INTO {table}(filepath_normalized, mode, size, mtime) VALUES (?, ?, ?, ?);",
(filename, *stats),
)
conn.commit()
def _get_stat_for_file(self, table, filename):
filename = str(pathlib.Path(filename).relative_to(self._path)).lower()
conn = self._conn
try:
c = conn.cursor()
c.execute(
f"SELECT mode, size, mtime FROM {table} WHERE filepath_normalized = ?",
(filename,),
)
results = c.fetchone()
if results:
stats = results[0:3]
mtime = int(stats[2]) if stats[2] is not None else None
stats = (stats[0], stats[1], mtime)
else:
stats = (None, None, None)
except Error as e:
logging.warning(e)
c = conn.cursor()
c.execute(
f"SELECT mode, size, mtime FROM {table} WHERE filepath_normalized = ?",
(filename,),
)
results = c.fetchone()
if results:
stats = results[0:3]
mtime = int(stats[2]) if stats[2] is not None else None
stats = (stats[0], stats[1], mtime)
else:
stats = (None, None, None)
return stats
@@ -636,7 +632,6 @@ class ExportDBInMemory(ExportDB):
def _open_export_db(self, dbfile):
""" open export database and return a db connection
if dbfile does not exist, will create and initialize the database
returns: connection to the database
"""
if not os.path.isfile(dbfile):

View File

@@ -177,7 +177,7 @@ class FileUtilMacOS(FileUtilABC):
Args:
src_file: image file to convert
dest_file: destination path to write converted file to
compression quality: JPEG compression quality in range 0.0 <= compression_quality <= 1.0; default 1.0
compression quality: JPEG compression quality in range 0.0 <= compression_quality <= 1.0; default 1.0 (best quality)
Returns:
True if success, otherwise False

View File

@@ -307,6 +307,7 @@ def export2(
dry_run=False,
touch_file=False,
convert_to_jpeg=False,
jpeg_quality=1.0,
):
""" export photo, like export but with update and dry_run options
dest: must be valid destination path or exception raised
@@ -348,6 +349,7 @@ def export2(
dry_run: (boolean, default=False); set to True to run in "dry run" mode
touch_file: (boolean, default=False); if True, sets file's modification time upon photo date
convert_to_jpeg: boolean; if True, converts non-jpeg images to jpeg
jpeg_quality: float in range 0.0 <= jpeg_quality <= 1.0. A value of 1.0 specifies use best quality, a value of 0.0 specifies use maximum compression.
Returns: ExportResults namedtuple with fields: exported, new, updated, skipped
where each field is a list of file paths
@@ -562,6 +564,7 @@ def export2(
convert_to_jpeg,
fileutil=fileutil,
edited=edited,
jpeg_quality=jpeg_quality,
)
exported_files = results.exported
update_new_files = results.new
@@ -590,6 +593,7 @@ def export2(
touch_file,
convert_to_jpeg,
fileutil=fileutil,
jpeg_quality=jpeg_quality,
)
exported_files.extend(results.exported)
update_new_files.extend(results.new)
@@ -618,6 +622,7 @@ def export2(
touch_file,
convert_to_jpeg,
fileutil=fileutil,
jpeg_quality=jpeg_quality,
)
exported_files.extend(results.exported)
update_new_files.extend(results.new)
@@ -823,6 +828,7 @@ def _export_photo(
convert_to_jpeg,
fileutil=FileUtil,
edited=False,
jpeg_quality=1.0,
):
""" Helper function for export()
Does the actual copy or hardlink taking the appropriate
@@ -842,6 +848,9 @@ def _export_photo(
touch_file: bool
convert_to_jpeg: bool; if True, convert file to jpeg on export
fileutil: FileUtil class that conforms to fileutil.FileUtilABC
edited: bool; set to True if exporting edited version of photo
jpeg_quality: float in range 0.0 <= jpeg_quality <= 1.0. A value of 1.0 specifies use best quality, a value of 0.0 specifies use maximum compression.
Returns:
ExportResults
@@ -949,7 +958,7 @@ def _export_photo(
fileutil.hardlink(src, dest)
elif convert_to_jpeg:
# use convert_to_jpeg to export the file
fileutil.convert_to_jpeg(src, dest_str)
fileutil.convert_to_jpeg(src, dest_str, compression_quality=jpeg_quality)
converted_stat = fileutil.file_sig(dest_str)
else:
fileutil.copy(src, dest_str, norsrc=no_xattr)