pacmanでfailed to commit transactionが出た場合の対処法

ごちゃまぜ技術系

先日パッケージアップデートをしようとしたら,なぜか上手くアップデートが走らず困りました.今後も同じことが起こりそうなので ちょくちょく起こるので解決方法を備忘録として残しておこうと思います.

発生した問題

いつものように以下で,パッケージアップデートを行います.

sudo pacman -Syu

実行すると,こんな感じのエラーがました.

:: Proceed with installation? [Y/n] Y
checking keyring...
checking package integrity...
loading package files...
checking for file conflicts...
error: failed to commit transaction (conflicting files)
node-gyp: /usr/lib/node_modules/node-gyp/node_modules/lru-cache/LICENSE.md exists in filesystem
npm: /usr/lib/node_modules/npm/docs/content/commands/npm-get.md exists in filesystem
npm: /usr/lib/node_modules/npm/docs/content/commands/npm-ll.md exists in filesystem
npm: /usr/lib/node_modules/npm/docs/content/commands/npm-set.md exists in filesystem
npm: /usr/lib/node_modules/npm/docs/content/commands/npm-trust.md exists in filesystem
npm: /usr/lib/node_modules/npm/docs/output/commands/npm-get.html exists in filesystem
npm: /usr/lib/node_modules/npm/docs/output/commands/npm-ll.html exists in filesystem
npm: /usr/lib/node_modules/npm/docs/output/commands/npm-set.html exists in filesystem
npm: /usr/lib/node_modules/npm/docs/output/commands/npm-trust.html exists in filesystem
npm: /usr/lib/node_modules/npm/lib/commands/trust/github.js exists in filesystem
npm: /usr/lib/node_modules/npm/lib/commands/trust/gitlab.js exists in filesystem
npm: /usr/lib/node_modules/npm/lib/commands/trust/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/lib/commands/trust/list.js exists in filesystem
npm: /usr/lib/node_modules/npm/lib/commands/trust/revoke.js exists in filesystem
npm: /usr/lib/node_modules/npm/lib/trust-cmd.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/@sigstore/sign/dist/config.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/@sigstore/sign/dist/external/rekor-v2.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/@sigstore/verify/dist/tlog/checkpoint.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/@sigstore/verify/dist/tlog/merkle.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/@sigstore/verify/dist/tlog/set.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/common-ancestor-path/LICENSE.md exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/common-ancestor-path/dist/commonjs/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/common-ancestor-path/dist/commonjs/package.json exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/common-ancestor-path/dist/esm/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/common-ancestor-path/dist/esm/package.json exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/glob/dist/commonjs/index.min.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/glob/dist/esm/index.min.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/LICENSE.md exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/commonjs/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/commonjs/index.min.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/commonjs/options.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/commonjs/package.json exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/commonjs/posix.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/commonjs/win32.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/esm/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/esm/index.min.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/esm/options.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/esm/package.json exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/esm/posix.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/isexe/dist/esm/win32.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/lru-cache/LICENSE.md exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/minipass-sized/dist/commonjs/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/minipass-sized/dist/commonjs/package.json exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/minipass-sized/dist/esm/index.js exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/minipass-sized/dist/esm/package.json exists in filesystem
npm: /usr/lib/node_modules/npm/node_modules/validate-npm-package-name/lib/builtin-modules.json exists in filesystem
Errors occurred, no packages were upgraded.

なんじゃこりゃ!!

原因

困ったらwikiを見ればなんとかなります.すると,以下の説明を発見.

pacman - ArchWiki

“This is happening because pacman has detected a file conflict, and by design, will not overwrite files for you”
なるほど,「ファイルが競合していて,仕様上,上書きできないよ」ということらしい.

解決方法

仕組みから理解したい人向け

先程のwikiの手順に従って,解決します.
” A safe way is to first check if another package owns the file (pacman -Qo /path/to/file). “
ということで,まず他のパッケージにエラーを吐いたファイルが所有されているかを以下のコマンドで確かめます.
オプションについて少し解説すると,-Qでパッケージデータベースに問い合わせ,oで指定したファイルを含んでいるパッケージを検索するという感じです.

pacman -Qo /path/to/file

(例)

pacman -Qo /usr/lib/node_modules/node-gyp/node_modules/lru-cache/LICENSE.md /usr/lib/node_modules/npm/docs/content/commands/npm-get.md ...

その結果,誰も所有していなければ(No package ownsのエラーが全部のファイルで出力される)OKです(所有されていたらバグレポートらしい).
そしたら,
“If the file is not owned by another package, rename the file which “exists in filesystem” and re-issue the update command.”
ということで,ファイル名称を変更してあげます.
なお,私は説明を読み間違えて,全部のファイルを消して対処したので,リネームで行けるかは未確認だが,流石に行けると思う.次出た時確認します.とりあえず解決できたので,rmの方を載せておきます. renameで動作確認済み)

sudo mv /path/to/file new/path/to/file(.bakを加えるとかする)

(例)
コマンドを作る際は,vscodeで縦選択やら置換などを使って,コマンドを作成しました(多分もっといい方法が在る気がするのでコメントなどで教えていただけると嬉しいです).

sudo rm /usr/lib/node_modules/node-gyp/node_modules/lru-cache/LICENSE.md /usr/lib/node_modules/npm/docs/content/commands/npm-get.md ...

最後に,いつものアップデートコマンドを打ち込みます.

sudo pacman -Syu

以下に楽をしたい人向けの方法を追記しておきました(2026/02/23).

楽をしたい人向け

「上の手順は,手間もかかるし面倒くさいして,でもこれ使うと早いんです.」ということで
原理なんて知らん,とりあえず動けばいいという方は,上の手順を一度に実行できるようにした以下のシェルスクリプトを実行して,もう一度pacman -Syuを実行すればいいです.
まず,以下のシェルスクリプトをコピーし適当なファイル(今回はcommand.sh とする)に保存します.

# 普通にアップデートコマンドをたたき,existes in filesystemとなる競合ファイルを,正規表現などをごちゃごちゃして抽出する
mapfile -t target_args < <( pacman -Syu --noconfirm 2>&1 | grep "exists in filesystem$" | sed -n 's/^[^:]*:[ \t]*\(.*[^ \t]\)[ \t]*exists in filesystem$/\1/p')
count1=${#target_args[@]}

if [ "$count1" -eq 0 ]; then
    echo "target_args is empty. No lines to process."
    exit 0
fi

# 一旦,上で求めた競合ファイルが全部No package ownsであるかを確認する.
flag="FALSE"
for arg in "${target_args[@]}"; do
    if pacman -Qo "$arg" 2>&1 | grep -q "No package owns"; then
        echo "Check OK (No package owns): $arg"
    else
        echo "WARNING (Package owns): $arg"
        flag="TRUE"
    fi
done

# 全部 No package ownsじゃない,つまり,依存がある場合終了
if [ "$flag" = "TRUE" ]; then
    echo "=> result: At least one file is owned by a package. Aborting rename."
    exit 1
fi

# 全て安全だった場合のみ、リネームを実行
echo "=> result: No files are owned by any package. Proceeding with rename..."
for arg in "${target_args[@]}"; do
    mv "$arg" "$arg.bak"
    echo "Renamed: $arg -> $arg.bak"
done

echo "Done. You can now run 'pacman -Syu' again."

次に,実行権限を以下で与えてあげます.

chmod +x command.sh 

最後に実行です.

sudo ./command.sh

あとはいつも通り以下でアップデートを走らせます.

sudo pacman -Syu

おわりに

今回はパッケージアップデートをしようとしたら失敗した話を書いてみました.
いつも動いてたコマンドが動かなくなると,環境壊したかと思って色々と焦りますよね.
同じ様に困っている人の助けになれば幸いです.
間違い等ありましたらコメントで教えていただけると嬉しいです.

コメント

タイトルとURLをコピーしました