はじめに
こんにちは。ジールの@________________-_です。
ローカルでairflow breezeを利用しておりますが、WebUIのAcitonsからDelete DAG
を実行するとエラーとなり削除できない事象が発生しました。
今までこんなこと無かった気がするので簡単に調査してみました。
悲しいです。。。
環境
Airflow breeze:v2.3.0.dev0
すべてデフォルト設定で利用
結論
tag付のDAGを削除しようとしていることが原因のようでした。
詳細
エラー内容を確認すると、sqlalchemy.exc.IntegrityError: (sqlite3.IntegrityError) FOREIGN KEY constraint failed
と記載があります。外部キー制約が原因で動作しないようです。
また、[SQL: DELETE FROM dag WHERE dag.dag_id IN (?)] [parameters: ('example_external_task_sensor_parent',)]
との記載もある為、dagテーブルのカラムに対して外部キーを設定しているテーブルが原因ぽいです。
早速テーブルを探してみたところdag_tag
テーブルを発見しました!
以下airflow breeze内部からsqliteにて確認しました。
cd ~/airflow
sqlite3 airflow.db
dag_tagテーブルのdag_idカラムに外部キーが設定されているのが分かります。
--表示モードをlineにする
sqlite> .mode line;
--dag_tagテーブルのDDLを表示
sqlite> select * from sqlite_master where type='table' and name='dag_tag';
>> type = table
>> name = dag_tag
>> tbl_name = dag_tag
>> rootpage = 4
>> sql = CREATE TABLE dag_tag (
>> name VARCHAR(100) NOT NULL,
>> dag_id VARCHAR(250) NOT NULL,
>> PRIMARY KEY (name, dag_id),
>> FOREIGN KEY(dag_id) REFERENCES dag (dag_id)
)
つまり、dag_tag
テーブルのdag_id
カラムがdag
テーブルのdag_id
カラムを参照した外部キーとなっている為、
先にdag_tag
テーブルのレコードを削除しないと、dag
テーブルからもレコードを削除できない状態です。
念のためsqlでも同様のエラーが発生するか試してみます。
--外部キーが有効になっているか確認
sqlite> PRAGMA foreign_keys;
>> foreign_keys = 0
--外部キーを有効にする
sqlite> PRAGMA foreign_keys=true;
sqlite> PRAGMA foreign_keys;
>> foreign_keys = 1
--dagテーブルからexample_external_task_sensor_parent DAGを削除
sqlite> delete from dag where dag_id = 'example_external_task_sensor_parent';
>> Error: FOREIGN KEY constraint failed --同様に外部キー制約エラー
同様のエラーが発生したので今度はdag_tagテーブルから先に削除してみます。
--dag_tagテーブルからexample_external_task_sensor_parent DAGを削除
sqlite> delete from dag_tag where dag_id = 'example_external_task_sensor_parent';
--dag_tagテーブルから削除後、dagテーブルからexample_external_task_sensor_parent DAGを削除
sqlite> delete from dag where dag_id = 'example_external_task_sensor_parent';
--エラーも発生せず削除が可能
改めて纏めると、
- DAGを作成すると、dagテーブルにレコードが登録される。
- DAGにtagを設定すると、dag_tagテーブルにもレコードが作成される。
- dag_tagテーブルのdag_idカラムは、dagテーブルのdag_idカラムを参照する外部キーとなっている。
- 上記の関係性から、tagのあるDAGを削除するには、dag_tagテーブルから対象レコードを削除した後にdagテーブルからも削除する必要がある。
- dagテーブルの対象レコードを先に削除しようとすると、dag_tagテーブルに対象レコードが存在している為外部キー制約エラーとなる。
テーブルの関係は以下の通り。
- dagテーブル:dagが登録されているテーブル
- dag_tagテーブル:dagのtagが登録されているテーブル。dag_idカラムはdagテーブルのdag_idカラムを参照した外部キー。
おわりに
実際のコードを読んでないので正確なことは言えませんが、
dag_tagテーブルのレコードを削除する前にdagテーブルのレコードを削除しようとしている為 エラーになっていると推測致しました。
ちなみに、DAGからtagを外すとWEBUIからも削除可能でした(tagをもともと設定していないDAGも削除可能)。
tagを設定していてもWebUIから削除出来る方法って何かあるんですかね???
おまけ コマンド実行の場合
コマンドでDAGを削除した場合はどうなるのか試してみました。
airflow dags delete -y example_external_task_sensor_parent
結果としては、同じエラーになったりならなかったり。。。謎です。
成功した場合は、
Remove 2 Record(s)
と表示されます。
ちなみに、tagを2個に増やすと、
Remove 3 Record(s)
と表示されます。
dagテーブルからdag1レコードと、dag_tagテーブルからdagのtag2レコードが削除されているものと思われます。
以上!
株式会社ジールでは、「ITリテラシーがない」「初期費用がかけられない」「親切・丁寧な支援がほしい」「ノーコード・ローコードがよい」「運用・保守の手間をかけられない」などのお客様の声を受けて、オールインワン型データ活用プラットフォーム「ZEUSCloud」を月額利用料にてご提供しております。
ご興味がある方は是非下記のリンクをご覧ください: