BigQueryの不要なデータセットを大量に削除したい
こちらは株式会社ガラパゴス(有志) Advent Calendar 2025の1日目の記事です。
先日チームメンバー全員が初めてリアル集合する機会があったのですが、近場なのに今まで一度も会っていなかったメンバーの見た目に驚きすぎて、その後に遠路はるばる来てくれたメンバーとの初対面の場でリアクションが薄くなってしまいました。せっかく初めて会えたのにその節は失礼だったかなあと反省してしまいます。
お詫びのしるしに、これまで一度もやってこなかった開発環境のBigQueryのお掃除でもしようと思いました。
プロジェクト内のデータセットを一覧で出力する
BigQueryを使い始めて今年で3年目、普段からきれいに使っているのでそこまで汚れていないはず、と思いつつまずはデータセットを眺めてみます。
プロジェクト内のデータセットを一覧で取得するクエリは以下のように記述できます。
SELECT
schema_name AS dataset_id,
catalog_name AS project_id,
location,
creation_time,
last_modified_time
FROM `project_id.region-asia-northeast1`.INFORMATION_SCHEMA.SCHEMATA
この結果をスプレッドシートに出力しました。上から見ていくとどれも見覚えがあり、今も使っているデータセットだったのですが、

こんな感じで、一番下に数千行の魔境が待ち構えていました。
全く記憶に無く、今まで一度も目に入ったことのないデータセットがずらり…。今までコンソールからデータセットを辿ることはありましたが、数が多すぎて一番下まで行くことは無かったので全く気づかなかったのだと思います。
とはいえデータ作成者には心当たりがあったので確認したところ、全て消して良いとのこと。一番下に表示されるよう目立たない名前をつけるあたりがずる賢い思慮深くて流石ですが、見つけてしまったからにはお掃除しなければです。
不要なデータセットをサクッと削除する
今回削除するデータセットの中にはそれぞれ数個〜十数個くらいのテーブルやビューが含まれています。流石にそれらを一つひとつ削除しているとクリスマスもお正月も過ぎてしまいますので、データセットごと一括で削除するクエリがあるか調べます(コンソールから手動でもデータセットごと削除できるのであるはず)。単一のデータセットを削除するクエリは以下のように書けると分かりました。
DROP SCHEMA IF EXISTS `<project_id>.dataset_name` CASCADE;
後は数千行だろうがこのクエリを縦に並べて実行するだけでOKだと思っていたのですが、2個以上並べると削除してくれませんでした。どうやらコンソールからは1つずつしか実行できないようです。
これでは手動で実行するのとほとんど変わらないので、さらに調べたところCloud Shellからbqコマンドを実行すれば削除できるとのことです(Pythonをローカルから実行する等、他の方法もあります)。
bq ls --project_id=<project_id> --format=json | \
python3 -c "
import sys, json
for d in json.load(sys.stdin):
dataset_id = d['datasetReference']['datasetId']
if dataset_id.startswith('zz'):
print(dataset_id)
" | \
while read dataset; do
bq rm -r -f -d <project_id>:$dataset
done
ちなみに紹介しているコマンドはzzから始まるデータセットを全て削除する条件になっていますので、用途に合わせて変更してください。しかしこちらのコマンドを実行したのですが、削除できませんでした。
実はbqコマンドで取得する件数には上限があり、デフォルトでは先頭の50件のみを取得します。50件を超える場合にはmax_resultsパラメータ(もしくは-n)で上限を指定する必要があるようです。
今回、開発環境のデータセットは消さなくてよいものを含めても1万で収まる件数でしたので、こんな感じですね。
bq ls --project_id=<project_id> --format=json --max_results=10000 | \
python3 -c "
import sys, json
for d in json.load(sys.stdin):
dataset_id = d['datasetReference']['datasetId']
if dataset_id.startswith('zz'):
print(dataset_id)
" | \
while read dataset; do
bq rm -r -f -d <project_id>:$dataset
done
ちなみに以下を実行すれば、削除対象のデータセットを事前に確認できます。
bq ls --project_id=<project_id> --format=json --max_results=10000 | \
python3 -c "
import sys, json
[print(d['datasetReference']['datasetId']) for d in json.load(sys.stdin) if d['datasetReference']['datasetId'].startswith('zz')]"
確認したところ不要なデータセットがちゃんと取れましたので、削除コマンドを実行して不要なデータセットを一掃できました!
(ちなみに数千個を消すには数時間くらいかかるため、途中でCloud Shellの接続が切れて何度か実行し直しました。このあたりの回避法もあるはずですが、今回は数回で済んだので手動でポチポチ再実行をかけました)
おわりに
軽く考えていたお掃除が予想以上に手間取りましたが、おかげで開発環境にあったデータセットの3割以上を断捨離できました。皆さまのプロジェクトにあるデータセットは確認できていますでしょうか?ぜひ年の瀬が迫る前に早めに一度チェックしてみてください。思わぬところから特大のゴミが出てくるかもしれませんよ!
それでは、皆さまも素敵な大掃除タイムをお過ごしください〜
Discussion