SQLFluffを導入してdbtの開発を加速させる
SQLFluffのルール集
SQLFluffのインストール
pip3 install sqlfluff
簡単に試してみる
その辺にあったこのSQLファイルで試してみる
with source as (
select * from {{ source('public', 'raw_orders') }}
),
renamed as (
select
id,
user_id,
order_date,
status
from source
)
select * from renamed
ではコーティングチェックを実施します。
sqlfluff lint stg_public__raw_orders.sql --dialect snowflake
sqlfluff lint stg_public__raw_orders.sql --dialect snowflake
== [stg_public__raw_orders.sql] FAIL
L: 1 | P: 1 | LT13 | Files must not begin with newlines or whitespace.
| [layout.start_of_file]
L: 22 | P: 1 | LT12 | Files must end with a single trailing newline.
| [layout.end_of_file]
All Finished 📜 🎉!
2つほど違反があった模様。LT13やL T12はルール集のリンクに全量ルールが記載されています。
英語でルール説明があり、ファイルの1行目にスペースはダメとか、ファイルの末尾は改行が必要とかって言われています。
これら違反箇所を修正してもOKなら以下コマンドを実行します。
sqlfluff fix stg_public__raw_orders.sql --dialect snowflake
sqlfluff fix stg_public__raw_orders.sql --dialect snowflake
==== finding fixable violations ====
== [stg_public__raw_orders.sql] FAIL
L: 1 | P: 1 | LT13 | Files must not begin with newlines or whitespace.
| [layout.start_of_file]
L: 22 | P: 1 | LT12 | Files must end with a single trailing newline.
| [layout.end_of_file]
==== fixing violations ====
2 fixable linting violations found
Are you sure you wish to attempt to fix these? [Y/n] ...
Attempting fixes...
Persisting Changes...
== [stg_public__raw_orders.sql] FIXED
Done. Please check your files to confirm.
All Finished 📜 🎉!
dbtテンプレートを利用してみる
pip3 install sqlfluff-templater-dbt
準備
.sqlfluffと.sqlfluffignoreを作成
dbtプロジェクト直下に「.sqlfluff」ファイルを作成し、そこにSQLfluffのルールを記述することで、独自のルール集を作ることができます。
touch .sqlfluff
touch .sqlfluffignore
.sqlfluffignoreの設定
.sqlfluffignoreファイルはプロジェクトの一部でない SQLファイルを参照するデプロイスクリプトがある場合、エラーになります。
この問題は、dbtプロジェクト以外のSQLファイルを.sqlfluffignoreに追加することで解決できます。
dbt_packages/
macros/
target/
dbt_modules/
.sqlfluffのテンプレート設定
.sqlfluff内にdbtプロジェクトのPATHを記載します。
[sqlfluff]のtemplatorにはdbt、dialectには今回duckdbを設定しました。
[sqlfluff:templater:dbt]
project_dir = /home/dbt/jaffle_shop_pj/jaffle_shop
profiles_dir = /home/dbt/jaffle_shop_pj/jaffle_shop
profile = jaffle_shop
target = dev
[sqlfluff]
templater = dbt
dialect = duckdb
オリジナルのルールを作成
よくあるルールだけで簡単に作成してみました。
コーディングルールを決める時は開発メンバーとの合意をもとに作成するのが良いと思います。
[sqlfluff]
templater = dbt
dialect = duckdb
[sqlfluff:rules:capitalisation.keywords]
capitalisation_policy = lower
[sqlfluff:templater:dbt]
project_dir = /home/dbt/jaffle_shop_pj/jaffle_shop
profiles_dir = /home/dbt/jaffle_shop_pj/jaffle_shop
profile = jaffle_shop
target = dev
[sqlfluff:indentation]
tab_space_size = 2
allow_implicit_indents = true
[sqlfluff:rules:aliasing.table]
aliasing = explicit
[sqlfluff:rules:aliasing.column]
aliasing = explicit
[sqlfluff:rules:capitalisation.identifiers]
capitalisation_policy = lower
[sqlfluff:rules:capitalisation.functions]
extended_capitalisation_policy = lower
[sqlfluff:rules:capitalisation.literals]
capitalisation_policy = lower
[sqlfluff:rules:capitalisation.types]
extended_capitalisation_policy = lower
Github Actionsとの連携
チームで開発する際はGithubの運用が多いと思います。
その場合、pushしたらSQLFluffを自動で実行してくれる仕組みがあると便利ですよね。
Github Actionsで自動化をやってみました。
dbtテンプレートを使う場合と使わない場合
dbtパッケージが必要なことは公式ドキュメントにも記載されていました。
準備
mkdir -p .github/workflows
cd .github/workflows
touch dbt-actions.yml
dbtテンプレートを使う場合
name: push_trigger_sqlfluff
on: push
jobs:
push:
runs-on: ubuntu-latest
steps:
- name: Check out
uses: actions/checkout@master
- uses: actions/setup-python@v1
with:
python-version: "3.10.x"
- name: Install packages
run: |
python3 -m pip install --upgrade pip
pip3 install sqlfluff
pip3 install sqlfluff-templater-dbt
pip3 install dbt-snowflake ※dbtのパッケージインストールしないとエラーとなる
- name: execute sqlfluff
working-directory: snowflake_pj
run: |
sqlfluff lint ./models/orders.sql
dbtテンプレートを使わない場合
name: push_trigger_sqlfluff
on: push
jobs:
push:
runs-on: ubuntu-latest
steps:
- name: Check out
uses: actions/checkout@master
- uses: actions/setup-python@v1
with:
python-version: "3.10.x"
- name: Install packages
run: |
python3 -m pip install --upgrade pip
pip3 install sqlfluff
pip3 install sqlfluff-templater-dbt
- name: execute sqlfluff
working-directory: snowflake_pj
run: |
sqlfluff lint ./models/orders.sql --rules L001 --dialect snowflake
[sqlfluff]
templater = dbt
dialect = snowflake
[sqlfluff:templater:dbt]
project_dir = ./
profiles_dir = ./
profile = snowflake_pj
target = dev
~略~
ディレクトリ構造(参考)
snowflake-dbt
|-- .github
| `-- workflows
| |-- dbt-actions.yml_bk
| `-- dbt-sqlfluff.yml
|-- README.md
|-- edr_target
|-- logs
`-- snowflake_pj
|-- .sqlfluff
|-- .sqlfluffignore
|-- README.md
|-- analyses
|-- dbt_packages
|-- dbt_project.yml
|-- models
|-- packages.yml
|-- profiles.yml
`--seeds
Discussion