PythonでDiffファイル(Patchファイル)を適用する方法: Pythonでパッチ適用

Python
この記事は約8分で読めます。
スポンサーリンク

今回は前回の記事で作成したDiffファイルを、Pythonを使ってマージする方法を紹介します。
Diffって何って思っている方や作成の方法がわからないよって方は、↓を見てみてください。

にいやんブログ
にいやんブログ

使用ライブラリ

今回使用するライブラリは以下です。

  • unidiff

インストールは以下で実施します。

pip install unidiff

プログラムと実行結果

プログラムと入力ファイル

プログラム

import os
from unidiff import PatchSet

DIFF_FILE = "test.diff"
TARGET_FILE = "Text2.txt"
CREATE_FILE = "Text_merge.txt"

with open(DIFF_FILE, 'r', encoding='utf-8') as f:
    diff_content = f.read()
    
with open(TARGET_FILE, 'r', encoding='utf-8') as f:
    original_content = f.readlines()

    
# unidiffオブジェクトの作成
patch =PatchSet(diff_content)

for patched_file in patch:
    for hunk in patched_file:
        for line in hunk:
            if line.is_added:
                original_content.insert(line.target_line_no-1, line.value)
            elif line.is_removed:
                original_content.pop(line.source_line_no-1)


with open(CREATE_FILE, 'w') as f:
    f.writelines(original_content)

入力ファイル

Text2.txt

こんにちは
今日は快晴です。

あしたも晴れるといいですね。
ではさようなら

test.diff

--- D:/Pythonテスト/unidiff/Text1.txt	Wed Feb 21 22:37:22 2024
+++ D:/Pythonテスト/unidiff/Text2.txt	Wed Feb 21 22:37:25 2024
@@ -1,5 +1,5 @@
 こんにちは
-今日は雨です。
+今日は快晴です。
 
-あしたは晴れるといいですね。
+あしたも晴れるといいですね。
 ではさようなら
スポンサーリンク

実行結果

Text2.txtに、test.diffの内容がマージされて、Text_merge.txtが生成されました。

生成ファイル

Text_merge.txt

こんにちは
今日は快晴です。

あしたも晴れるといいですね。
ではさようなら
スポンサーリンク

プログラム解説

プログラムの解説です。

このプログラムは以下のような流れで処理されています。

  1. 差分ファイル(Diffファイル)の読み出し
  2. 元ファイルの読み出し
  3. パッチセットのロードとパッチセット内容から元ファイルにデータをマージ
  4. マージデータの書き出し

では順に行きます。

ファイルの読み出し

やっていることは同じですので、差分ファイル(Diffファイル)と元ファイルの読み出しは一気に説明します。

DIFF_FILE = "test.diff"
TARGET_FILE = "Text2.txt"

with open(DIFF_FILE, 'r', encoding='utf-8') as f:
    diff_content = f.read()
    
with open(TARGET_FILE, 'r', encoding='utf-8') as f:
    original_content = f.readlines()

DIFF_FILE とTARGET_FILE のファイルを、データとして読み込みしています。
※encoding=’utf-8’は、エンコードを指定しないとエラーになったので、入れています。

パッチセットのロードとパッチセット内容から元ファイルにデータをマージ

以下が、パッチセットの読み出しとマージ処理になります。


from unidiff import PatchSet

patch =PatchSet(diff_content)

for patched_file in patch:
    for hunk in patched_file:
        for line in hunk:
            if line.is_added:
                original_content.insert(line.target_line_no-1, line.value)
            elif line.is_removed:
                original_content.pop(line.source_line_no-1)

以下が、パッチセットのロード。

patch =PatchSet(diff_content)

以下が、マージ処理になります。
パッチセット内容を順にロードして、挿入部分と削除部分をオリジナルのデータに書き込み・削除してデータを成形していっています。

for patched_file in patch:
    for hunk in patched_file:
        for line in hunk:
            if line.is_added:
                original_content.insert(line.target_line_no-1, line.value)
            elif line.is_removed:
                original_content.pop(line.source_line_no-1)

マージデータの書き出し

最後は、3で生成したデータをファイルに書き出しして終了です。

CREATE_FILE = "Text_merge.txt"

with open(CREATE_FILE, 'w') as f:
    f.writelines(original_content)

CREATE_FILE で指定したファイルに、書き込みしています。

スポンサーリンク
スポンサーリンク

まとめ

今回は、DiffファイルをPythonを使って、元ファイルにマージすることにチャレンジしてみました。
このunidiffについては、あまり参考にできる記事などもなく結構苦労しましたが、何とかマージすることができました。
もし、同じように悩んでいる方がいればぜひ参考にしてください!!

最後に、Pythonの基礎を学びたい方は以下がおすすめです。私も持っていてたまに眺めて勉強していますものですのでぜひ購入して学習してみてください。

コメント

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