Copy metadata of images in one directory to images in another directory

Started by tsalt, November 17, 2020, 11:56:41 AM

Previous topic - Next topic

tsalt

Hi everyone - I'm new here and only have a little experience working with applications from the command line. My other scripting experience is mainly with Python but also R and Javascript.

In my case, I have 2500 .tiff images with metadata. I'm processing these images with OpenCV in Python, and OpenCV creates a copy of the images but loses the metadata, so I need to copy the metadata from the original source file to the new processed file. The original images are in a folder and the processed images are in a different folder. The images have the same name, i.e. IMG_0005.tif in both folders. My organization is exif tool path: /exiftool-12.10/exiftool.pl.exe, source image path: /exiftool-12.10/images/IMG_0005_1.tif, processed image path /exiftool-12.10/degrade13x/IMG_0005_1.tif.

I've been able to copy the metadata from a single .tif image to another using the -tagsFromFile command, but I have no idea how to batch process this from the command line. I attempted to use the Python wrapper, PyExifTool, but I got an error "TypeError: sequence item 0: expected a bytes-like object, str found" when executing -tagsFromFile. I'll attach my code below for reference (I replaced the base path of ExifTool with something generic).


import os
import exiftool as et

base_dir = 'directory'
os.chdir(base_dir)

input_images = os.path.join(base_dir, 'images')
degrade13x = os.path.join(base_dir, 'degrade13x')

og_files = os.listdir(input_images)
degraded_files = os.listdir(degrade13x)

for original, degraded in zip(og_files, degraded_files):
    if original != degraded:
        raise Exception(original + " does not match " + degraded)
    else:
        print(original + " matches " + degraded)
        with et.ExifTool(r"C:\directory\exiftool-12.10\exiftool.pl.exe") as et:
            print("Copying exif to destination file. ")
            og = os.path.join("images", original)
            print("Original image path: " + og)
            deg = os.path.join("degrade13x", degraded)
            print("Degraded image path: " + deg)
            et.execute("-tagsFromFile", og, deg)


Here's the error:

IMG_0005_1.tif matches IMG_0005_1.tif
Copying exif to destination file.
Original image path: images\IMG_0005_1.tif
Degraded image path: degrade13x\IMG_0005_1.tif
---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-5-0507d6b498e2> in <module>
     11             deg = os.path.join("degrade13x", degraded)
     12             print("Degraded image path: " + deg)
---> 13             et.execute("-tagsFromFile", og, deg)
     14
     15 #         et.terminate()

~\.conda\envs\conda_env\lib\site-packages\exiftool.py in execute(self, *params)
    220         if not self.running:
    221             raise ValueError("ExifTool instance not running.")
--> 222         self._process.stdin.write(b"\n".join(params + (b"-execute\n",)))
    223         self._process.stdin.flush()
    224         output = b""

TypeError: sequence item 0: expected a bytes-like object, str found


The following command has worked successfully in the command prompt:

C:\directory\exiftool-12.10> exiftool.pl  -TagsFromFile images/IMG_0005_1.tif -all:all degrade13x/IMG_0005_1.tif


I understand that this isn't a forum for the Python wrapper of ExifTool, so I expect I may get replies referring to solutions with the command line, and that's okay. I'm willing to try/learn anything, as I haven't found another solution for copying exif data between .tif files. I figure my Python code can at least give reference to what I'm trying to do. My OS is Windows Server 2019.

I appreciate any and all help!

StarGeek

I can't help with the python code, but on the command line the command would be very simple.  Assuming your current directory is /exiftool-12.10, then your command would be
exiftool.pl -TagsFromFile images/%f.%e -all:all degrade13x/

The command works like this: for every file it finds in the degrade13x directory, it looks for a file in the images directory with the same base filename %f and the same extension %e.
* Did you read FAQ #3 and use the command listed there?
* Please use the Code button for exiftool code/output.
 
* Please include your OS, Exiftool version, and type of file you're processing (MP4, JPG, etc).

tsalt

Wow, that was very simple, and it worked! Thank you, that saves me a ton of time!

tsalt

Quote from: StarGeek on November 17, 2020, 12:10:55 PM
I can't help with the python code, but on the command line the command would be very simple.  Assuming your current directory is /exiftool-12.10, then your command would be
exiftool.pl -TagsFromFile images/%f.%e -all:all degrade13x/

The command works like this: for every file it finds in the degrade13x directory, it looks for a file in the images directory with the same base filename %f and the same extension %e.

So I thought this worked, but I'm missing a very specific tag that I need in the destination images. The tag is Xmp.Camera.BandName.

I tried using the -a and -unsafe options and those didn't work. I also tried exiftool.pl -TagsFromFile images/%f.%e '-xmp:all<all' degrade13x/ but it's returning The system cannot find the file specified.
Do you have any ideas on how I can get this tag from the source images to the destination?

Thank you

Phil Harvey

ExifTool has no "BrandName" tag pre-defined, so you will have to create a user-defined tag to write this.  See the sample config file for examples.

QuoteThe system cannot find the file specified.

This warning isn't from ExifTool.  But check your quoting.  You should be using double quotes if you are running in cmd.exe under Windows.

- Phil
...where DIR is the name of a directory/folder containing the images.  On Mac/Linux, use single quotes (') instead of double quotes (") around arguments containing a dollar sign ($).

tsalt

Hi Phil,

Thank you for this - you are correct about the quotes, I needed to use double.

The tags I am referring to are for Pix4D files, and I found some posts you made previously. I will try the config file you posted a couple of years back and hopefully, that will solve my issues.

Quote from: Phil Harvey on November 27, 2020, 12:55:51 PM
ExifTool has no "BrandName" tag pre-defined, so you will have to create a user-defined tag to write this.  See the sample config file for examples.

QuoteThe system cannot find the file specified.

This warning isn't from ExifTool.  But check your quoting.  You should be using double quotes if you are running in cmd.exe under Windows.

- Phil

StarGeek

Quote from: tsalt on November 28, 2020, 01:52:37 PM
The tags I am referring to are for Pix4D files, and I found some posts you made previously. I will try the config file you posted a couple of years back and hopefully, that will solve my issues.

I believe there are two older versions posted in the forums, but I believe the one on GitHub is more complete and up to date.
* Did you read FAQ #3 and use the command listed there?
* Please use the Code button for exiftool code/output.
 
* Please include your OS, Exiftool version, and type of file you're processing (MP4, JPG, etc).

tsalt

Thank you, I'll try with the config from Github. I really appreciate the help.

Quote from: StarGeek on November 28, 2020, 02:04:09 PM
Quote from: tsalt on November 28, 2020, 01:52:37 PM
The tags I am referring to are for Pix4D files, and I found some posts you made previously. I will try the config file you posted a couple of years back and hopefully, that will solve my issues.

I believe there are two older versions posted in the forums, but I believe the one on GitHub is more complete and up to date.