Immichのフォルダ配下すべての写真・動画アップロードスクリプト

投稿日:

更新日:

カテゴリ:

先日紹介した写真管理ソリューションのImmichですが、バージョン1.95.1では、PCからアップロードする際、ブラウザで直接アップロードできますし、しかも次のように、同時アップロードを随時調整できて、とても効率的で柔軟です。

しかし、ちょっとした問題として、アップロードの時にファイルしか選択できません。

日付ごとのフォルダに分けられた写真をアップロードしたいですが、フォルダを選択できないです。
数年分の写真がありますので、日ごとに選択するのは結構骨が折れる作業になりそうです。

そこで調べたところ、APIが用意されており、公式では「Python File Upload」のサンプルまで用意されてます。
ファイルごとのアップロードではありますが、最近話題のGeminiの力を借りてフォルダごとアップロードのPythonスクリプトを作りましたのでこちらで共有します。

APIキー作成

Immichの管理画面にログインしたら、次のように操作すればAPIキーを作成できます。
APIキーは作成直後の画面でしか表示されないようですので、お忘れなく保存しておきましょう。

アップロードのPythonスクリプト

ソースは以下です。アップロードはマルチスレッドで行います。

#!/usr/bin/python3

import requests
import os
from datetime import datetime
from concurrent.futures import ThreadPoolExecutor

API_KEY = 'YOUR_API_KEY'                # 上で作ったAPIキーに置き換えてください
BASE_URL = 'http://127.0.0.1:2283/api'  # ご自身の環境に合わせて変更してください


def upload(file):
    stats = os.stat(file)

    headers = {"Accept": "application/json", "x-api-key": API_KEY}

    data = {
        "deviceAssetId": f"{file}-{stats.st_mtime}",
        "deviceId": "python",
        "fileCreatedAt": datetime.fromtimestamp(stats.st_mtime),
        "fileModifiedAt": datetime.fromtimestamp(stats.st_mtime),
        "isFavorite": "false",
    }

    files = {"assetData": open(file, "rb")}

    response = requests.post(
        f"{BASE_URL}/asset/upload", headers=headers, data=data, files=files
    )

    print(response.json())
    # {'id': 'ef96f635-61c7-4639-9e60-61a11c4bbfba', 'duplicate': False}
    print(f"アップロード成功: {file} ({os.path.getsize(file)} bytes)")


def main(dirpaths):
    # アップロード対象となるファイル一覧を取得
    file_paths = []
    for dirpath in dirpaths:
        for dirpath, dirnames, filenames in os.walk(dirpath):
            file_paths.extend(
                [os.path.join(dirpath, filename) for filename in filenames]
            )

    # マルチスレッド処理
    with ThreadPoolExecutor(max_workers=os.cpu_count()) as executor:
        executor.map(upload, file_paths)


if __name__ == "__main__":
    # スクリプトの引数を受け取る

    import sys

    dirpaths = sys.argv[1:]

    main(dirpaths)

上記のスクリプトをimmich-upload.pyというファイル名だとすれば、次のように実行できます。

python immich-upload.py <フォルダパス1> <フォルダパス2> <フォルダパス3> ...

実行結果は次のようになります。

{'id': '9f66a2d7-3bfd-4fc8-8139-41377728cf79', 'duplicate': False}
アップロード成功: <パス>/<ファイル名> (<ファイルサイズ> bytes)

同じファイルを2回目以降アップロードされた場合、上記結果の’duplicate’はTrueになりますが、エラーになることはありません。


投稿日

カテゴリー:

投稿者:

タグ:

コメント

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です