Pythonで写真と動画を日付ごとに整理する方法

markdown-img-paste-20210821120904460.webp
目次

はじめに

近年のデジタルデバイスの普及により、私たちの身の回りにはさまざまな写真や動画が増えています。スマホやデジカメで撮影した写真を整理する方法については悩む人も多いでしょう。今回は、Pythonを使って写真や動画を日付ごとにフォルダ分けして整理する方法を紹介します。

コード全体

出来上がったコードの全体像はこちらです。 Githubにも上げておきました。(随分前に)

Github:PhotoSorting

# -*- coding: utf-8 -*-
import sys
import os
import re
import shutil
import glob
import datetime
from PIL import Image
from PIL.ExifTags import TAGS
from tqdm import tqdm
import ffmpeg
import json

def get_exif(img,file):
    exif = img._getexif()
    try:
        for id,val in exif.items():
            tg = TAGS.get(id,id)
            if tg == "DateTimeOriginal":
                return val
    except AttributeError:
            if os.path.exists(file) :
                dt = datetime.datetime.fromtimestamp(os.stat(file).st_mtime)
                key = dt.strftime('%Y:%m:%d %H:%M:%S')
                return key
    if os.path.exists(file) :
        dt = datetime.datetime.fromtimestamp(os.stat(file).st_mtime)
        key = dt.strftime('%Y:%m:%d %H:%M:%S')
    return key

def list_files(dir,func):
    for file in dir:
        try:
            img = Image.open(file)
        except:
            continue
        datetimeinfo = func(img,file)
        yield (file, datetimeinfo)
        img.close()

def make_folda(taginfo):
    date_str = re.split(':|\s', taginfo[1])
    year = date_str[0]
    month = date_str[1]
    date = str(date_str[1]) + str(date_str[2])
    time = date_str[3] + '_'+ date_str[4] + '.'+ date_str[5]
    fd_path = '整理済み/写真/' + str(year) +'/'+ str(month)
    datetime = str(year) +'-'+ str(date) + '-' + str(time)
    os.makedirs(fd_path, exist_ok=True )
    return fd_path,datetime

def make_folda_douga(taginfo,datatimes):
    date_str = re.split(':|\s|-|T|\.', datatimes)
    year = date_str[0]
    month = date_str[1]
    date = str(date_str[1]) + str(date_str[2])
    time = date_str[3] + '_'+ date_str[4] + '.'+ date_str[5]
    fd_path = '整理済み/動画/' + str(year) +'/'+ str(month)
    datetimestr = str(year) +'-'+ str(date) + '-' + str(time)
    os.makedirs(fd_path, exist_ok=True )
    return fd_path, datetimestr

def find_metadata_atom(file, name):
       atom = file.find('.//%s//data' % name)
       return atom.get_attribute('data')

def getdatetimeinJSON(json_dict):
    if 'format' not in json_dict.keys():
        return None
    if 'tags' not in json_dict['format'].keys():
        return None
    if 'creation_time' not in json_dict['format']['tags'].keys():
        return None
    return json_dict['format']['tags']['creation_time']

def main():
    id = 0
    print("写真(jpg)の整理中")
    target_path = glob.glob('.\imgs\**\*.webp', recursive=True)
    list_jpg = list_files(target_path,get_exif)
    bar = tqdm(total = len(target_path))
    for taginfo in list_jpg:
        mv_path, datetime = make_folda(taginfo)
        id = id + 1
        new_path = shutil.copy2(taginfo[0], mv_path + '/' +datetime+'_'+str(id) +'.webp')
        bar.update(1)

    print("写真(png)の整理中")
    target_path_png = glob.glob('.\imgs\**\*.webp', recursive=True)
    list_png = list_files(target_path_png,get_exif)
    bar = tqdm(total = len(target_path_png))
    list_png = list_files(target_path_png,get_exif)
    for taginfo in tqdm(list_png):
        mv_path, datetime = make_folda(taginfo)
        id = id + 1
        new_path = shutil.copy2(taginfo[0], mv_path + '/' +datetime+'_'+str(id) +'.webp')
        bar.update(1)

    print("写真(HEIC)の整理中")
    target_path_heic = glob.glob('.\imgs\**\*.heic', recursive=True)
    list_png = list_files(target_path_heic,get_exif)
    bar = tqdm(total = len(target_path_heic))
    list_heic = list_files(target_path_heic,get_exif)
    for taginfo in tqdm(list_heic):
        mv_path, datetime = make_folda(taginfo)
        id = id + 1
        new_path = shutil.copy2(taginfo[0], mv_path + '/' +datetime+'_'+str(id) +'.heic')
        bar.update(1)

    print("動画(mp4)の整理中")
    target_path_mp4 = glob.glob('.\imgs\**\*.mp4', recursive=True)
    for path in tqdm(target_path_mp4):
        video_info = ffmpeg.probe(path)
        json_dict = json.loads(json.dumps(video_info))
        datatimes = getdatetimeinJSON(json_dict)
        mv_path, datetimestr = make_folda_douga(path,datatimes)
        id = id + 1
        new_path = shutil.copy2(path, mv_path + '/' +datetimestr+'_'+str(id) +'.mp4')

    print("動画(mov)の整理中")
    target_path_mov = glob.glob('.\imgs\**\*.mov', recursive=True)
    for path in tqdm(target_path_mov):
        try:
            video_info = ffmpeg.probe(path)
            json_dict = json.loads(json.dumps(video_info))
            datatimes = getdatetimeinJSON(json_dict)
            mv_path, datetimestr = make_folda_douga(path,datatimes)
            id = id + 1
            new_path = shutil.copy2(path, mv_path + '/' +datetimestr+'_'+str(id) +'.mov')
        except:
            print(path)

if __name__ == '__main__':
    main()

準備

pip install ffmpeg
pip install pillow
pip install tqdm

動画から情報取得するためにffmpegを使用しています。 画像は定番のpillowを使い、tqdmは進捗バーを出すのに使っています。

実行画面

動作中の画面はこんな感じです。

実行画面1

年と月ごとに写真を分類して移動させます。

実行画面2 ]

ファイル名は一律で日時から作られるようにしています。

実行画面4

まとめ

今回の記事では、Pythonを使って写真や動画を日付ごとに整理する方法を紹介しました。ffmpegやPillowなどのライブラリを利用して、Exif情報から日付情報を取得し、ファイルを適切なフォルダに移動させるプログラムを作成しました。この方法を使えば、大量の写真や動画を簡単に整理することができます。ただし、動画のエラー処理がまだ甘いため、今後の改善が必要です。

Related Post

> Pythonで写真と動画を日付ごとに整理する方法
PCでPSVRのステレオカメラを使ってみた
> Pythonで写真と動画を日付ごとに整理する方法
競馬情報のスクレイピングと機械学習

おすすめの商品

>