---
title: "dbt docsの使い方：generate・serveでリネージを作り社内に公開する手順【v2対応】"
url: "https://www.issoh.co.jp/tech/details/19599/"
published: 2026-11-11
updated: 2026-11-11
categories: ["データベース"]
publisher: "株式会社一創"
---

# dbt docsの使い方：generate・serveでリネージを作り社内に公開する手順【v2対応】

dbt docsは、モデルの説明・列・テスト・リネージを1つのWebサイトにまとめる機能です。2026年11月時点では、dbt-core 1.12系の「Docs v1」と、dbt v2の「Docs v2」で生成物も既定のポートも違います。この記事では公式ドキュメントとdbtのソースコードをもとに、descriptionとdocsブロックの書き方、`dbt docs generate`と`dbt docs serve`のフラグ、列レベルのリネージの出し方、GitHub PagesやS3とCloudFrontで社内に公開する手順を、コピーして使える形で整理しました。

## まとめ：dbt docsは版で生成物が変わり、社内公開は配信先と認証で決まる

手元で確かめるだけなら、`dbt docs generate`のあとに`dbt docs serve`を打てばブラウザが開きます。v1は8080番、v2は8580番です。

社内に見せる段階では`dbt docs serve`を使いません。公式ドキュメントはこのコマンドをローカルの開発用途に限定しています。生成した静的ファイルを、アクセス制御のできる配信先に置きます。

配信先の選び方は単純です。GitHub Enterprise Cloudを契約していればGitHub Pagesを非公開にでき、それ以外はS3とCloudFrontで認証を掛けます。dbt platformのStarter以上を契約しているなら、自前の公開はやめてCatalogと閲覧専用シートに任せる方が保守の手間がかかりません。

## dbt docsの生成物を比較：dbt-core 1.12系とdbt v2の違い

手順に入る前に、手元のdbtがどちらの系統かを確かめます。`dbt --version`で「Core: 1.12.x」と出ればv1、2.0系ならv2です。入れ分けの手順は[dbt Coreの使い方](https://www.issoh.co.jp/tech/details/19592/)で解説しています。

### Docs v1のJSONとDocs v2のParquet索引を読む仕組み

[About dbt docs commands](https://docs.getdbt.com/reference/commands/cmd-docs)によると、v1の`dbt docs generate`はサイト本体の`index.html`を`target/`へコピーし、プロジェクトをコンパイルして`manifest.json`を書き、DWHのメタデータを問い合わせて`catalog.json`を作ります。ブラウザはこの2つのJSONを丸ごと読み込みます。

v2の生成物はJSONではなくParquetの索引です。ブラウザがDuckDB-WASMでParquetを直接読むので、モデル数の多い大きなプロジェクトでも表示が重くなりにくい作りです。[dbt Information Schema](https://docs.getdbt.com/docs/build/dbt-information-schema)は、manifest.jsonとcatalog.jsonで合計約70MBのプロジェクトが約5MBに収まる例を示しています。

| 項目          | Docs v1（dbt-core 1.12系） | Docs v2（dbt v2）       |
| ----------- | ----------------------- | --------------------- |
| 主な生成物       | HTML本体・2種のJSON          | HTML本体・アセット・Parquet索引 |
| serveの既定ポート | 8080                    | 8580                  |
| 列レベルのリネージ   | なし                      | フラグ指定で表示              |
| 1ファイル化      | –static                 | –output-dirでフォルダ出力    |

表のHTML本体は両系統とも`index.html`です。v1の2種のJSONは`manifest.json`と`catalog.json`、v2のアセットは`assets/`、Parquet索引は`index/`です。既存の公開手順が`target/`を配信先へ移すだけなら、v2でもそのまま動きます。公式ドキュメントはv2の出力先をv1と同じ`target/`の配置にそろえたと説明しています。

### dbt platformのv2ジョブで静的サイトからCatalogへ切り替わる条件

dbt platformのジョブでv2を使う場合、ジョブの手順に`dbt docs generate`を足しても静的サイトは作られません。dbtは代わりに`dbt compile --write-catalog`を実行し、Catalogを見るよう案内します。Docs v2はローカルと自前のパイプライン専用で、dbt platformでは提供されていません。

dbt platform上で過去に作ったdocsのジョブをv2へ移すと、`index.html`を前提にした後続の公開処理が空振りします。移行の前に、そのジョブの成果物を誰が見ているかを洗い出しておきます。

## descriptionとdocsブロックをYAMLに書き、モデルと列の説明を整える手順

dbt docsに表示される説明文は、テストと同じYAMLに書きます。コマンドを打つ前に、ここを整えておかないと空の画面が並ぶだけになります。

### schema.ymlの説明をdoc関数でMarkdownに分けて管理する書き方

[About documentation](https://docs.getdbt.com/docs/build/documentation)のとおり、モデルと列には`description:`を足します。数行を超える説明は`.md`ファイルのdocsブロックに逃がし、YAMLからは`doc()`関数で参照します。

```
# models/marts/_marts.yml
models:
  - name: fct_daily_sales
    description: '{{ doc("fct_daily_sales") }}'
    columns:
      - name: order_date
        description: 注文日（JST）。返品の計上日ではない
        data_tests:
          - not_null
      - name: sales
        description: status が completed の注文の税込金額の合計

-- models/marts/fct_daily_sales.md
{% docs fct_daily_sales %}
日別の売上集計。毎朝6時の本番ジョブで更新する。
- 返品は含めない（返品は fct_daily_returns を参照）
- 問い合わせ先：データ基盤チーム
{% enddocs %}
```

docsブロックの名前に使えるのは英数字とアンダースコアだけで、数字から始められません。1.12からは`allow_jinja_file_extensions: true`を設定すると`.md.j2`などの拡張子も使えます。

### \_\_overview\_\_ブロックで社内向けトップページを差し替える設定

何も設定しないと、dbt docsのトップページにはdbt自身の説明が出ます。社内に公開するなら、`__overview__`という名前のdocsブロックで差し替え、命名規則・更新時刻・問い合わせ先を最初に見せます。

```
# dbt_project.yml（docs/ フォルダに置く場合だけ必要）
docs-paths: ["docs"]

-- docs/overview.md
{% docs __overview__ %}
# 販売データ基盤
- stg_ は取り込み直後の整形、fct_ と dim_ が分析用の表です
- 本番の更新は毎朝6時。遅延は #data-infra チャンネルで告知します
{% enddocs %}
```

[docs-paths](https://docs.getdbt.com/reference/project-configs/docs-paths)を設定していなければ、dbtはmodelsなどのリソース用フォルダからdocsブロックを探します。`models/overview.md`に置けば設定は要りません。逆に`docs-paths`を書くとそのフォルダしか探さなくなるので、モデル横の`.md`が見つからなくなる点に気をつけます。

### persist\_docsで説明をDWHの列コメントにも書き戻す設定と対応アダプター

BIツールやSQLクライアントから直接テーブルを見る人には、dbt docsのサイトは届きません。[persist\_docs](https://docs.getdbt.com/reference/resource-configs/persist%5Fdocs)を有効にすると、descriptionがテーブルと列のコメントとしてDWHにも書き込まれます。

```
# dbt_project.yml
models:
  shop_dbt:
    marts:
      +persist_docs:
        relation: true
        columns: true
```

対応するのはPostgreSQL・Redshift・Snowflake・BigQuery・Databricks・Apache Spark・Starburst Galaxyです。sourcesには効きません。Snowflakeでは`ca_net_ht_N`のように大文字と小文字が混ざった列名だとコメントが付かないため、YAMLの列名を小文字にそろえるか`quote: true`を指定します。

## dbt docs generateとserveをローカルで動かし、リネージを確かめる

説明を書いたら、手元でサイトを作って表示を確かめます。v1とv2でフラグが違うので、分けて書きます。

### v1のdocs generateの3段階と生成対象・問い合わせを絞るフラグ

v1では、先に`dbt build`でテーブルを作っておきます。catalog.jsonはDWHに実在するテーブルの列を読むため、未作成のモデルはYAMLに書いた列しか表示されません。

```
dbt build                                   # テーブルとビューを先に作る
dbt docs generate                           # index.html・manifest.json・catalog.json
dbt docs generate --select +fct_daily_sales # catalogを指定モデルと上流に絞る
dbt docs generate --empty-catalog           # DWHに問い合わせない（開発中のリネージ確認用）
dbt docs generate --no-compile              # 再コンパイルを省く
dbt docs generate --static                  # target/static_index.html を1ファイルで出力
```

`--select`で絞るのはcatalog.jsonだけで、manifest.jsonは全体のままです。公式ドキュメントによると、選んだノードが100未満ならDWH側でWHERE句を使って絞り込み、100以上なら対象スキーマを全件読んでからメモリ上で絞ります。`--static`はmanifestとcatalogを埋め込んだHTMLを書き出し、[1.12系のソースコード](https://github.com/dbt-labs/dbt/blob/1.12.latest/core/dbt/task/docs/generate.py)ではファイル名が`static_index.html`です。メールやファイル共有で1枚だけ渡したいときに使います。

### dbt docs serveの8080・8580と待ち受け先・ポートの指定

v1の`dbt docs serve`は`target/`を起点に8080番でWebサーバーを立て、既定のブラウザを開きます。1.8.1以降は待ち受けが`127.0.0.1`なので、同じネットワークの別の端末からは見えません。

```
# v1（dbt-core 1.12系）
dbt docs serve --port 8001 --no-browser
dbt docs serve --host ""          # 全インターフェースで待ち受け（検証時のみ）

# v2（dbt v2）
dbt docs serve --port 8081
dbt docs serve --target-path ~/work/internal-analytics/target
```

v2の既定ポートは8580です。v2の`serve`はサイトが無いか索引より古いと自動で作り直すため、`generate`を打ち忘れても動きます。v1は`catalog.json`が無いとエラーで止まります。

### Docs v2の列レベルリネージに必要なビルドのフラグと静的解析の設定

Docs v2の目玉は列単位のリネージです。ただし既定では出ません。ビルドの段階でdbt Information Schemaを書き出し、静的解析を`strict`にしてから、コンパイルを省いてサイトを作ります。

```
dbt build --generate-info-schema --static-analysis strict
dbt docs generate --no-compile --output-dir site
dbt docs serve
```

メタデータは`target/info_schema/v1/`にParquetで書かれ、DWHの計算資源は使いません。フラグを付けずに作ったサイトでは、列リネージの画面が空表示ではなく非表示になります。「出ない」と迷ったら、まずビルドのフラグを疑います。2026年10月公開の一部の解説記事には`--write-index`という別のフラグ名が出てきますが、11月時点の公式ドキュメントの表記は`--generate-info-schema`です。手元の版では`dbt build --help`で確かめてください。静的解析の厳しさを上げると型の合わないSQLが解析段階で落ちるので、移行の注意点は[dbt Fusionとは](https://www.issoh.co.jp/tech/details/19593/)を参照してください。

## 社内公開：GitHub ActionsのPages配信とS3・CloudFrontの認証

手元で表示を確かめたら、チームで見られる場所へ置きます。ここで手を抜くと、テーブル定義やSQLが社外から読める状態になります。

### docs serveを本番に使わず、公開するファイルをtarget全体から絞る

[View documentation](https://docs.getdbt.com/docs/build/view-documentation)は、`dbt docs serve`をローカルの開発用途だけに使うよう注意しています。[1.12系のserve.py](https://github.com/dbt-labs/dbt/blob/1.12.latest/core/dbt/task/docs/serve.py)の中身は、Python標準の`SimpleHTTPRequestHandler`を立てているだけです。認証もHTTPSもありません。

配信先に置くファイルも絞ります。v1で必要なのは`index.html`・`manifest.json`・`catalog.json`の3つです。`target/`には`compiled/`と`run/`に展開済みのSQL、`run_results.json`に実行結果も入っており、まとめて上げると見せる必要のないものまで公開されます。v2は`--output-dir site`で出した`site/`だけを上げます。

### GitHub ActionsでビルドしPagesへデプロイするワークフローの例

本番のテーブルがすでにある前提で、mainブランチへのマージごとにdocsを作り直してGitHub Pagesへ出す例です。`dbt docs generate`はテーブルを作らず、既存のテーブルのメタデータを読むだけなので、本番ジョブとは別に流せます。[カスタムワークフローでのPages公開](https://docs.github.com/en/pages/getting-started-with-github-pages/using-custom-workflows-with-github-pages)の手順に沿い、[upload-pages-artifact](https://github.com/actions/upload-pages-artifact)と[deploy-pages](https://github.com/actions/deploy-pages)を使います。

```
# .github/workflows/dbt-docs.yml
name: dbt-docs
on:
  push:
    branches: [main]
  workflow_dispatch:
permissions:
  contents: read
  pages: write
  id-token: write
concurrency:
  group: pages
  cancel-in-progress: false
jobs:
  build:
    runs-on: ubuntu-latest
    env:
      DBT_ENV_SECRET_PG_PASSWORD: ${{ secrets.DBT_PG_PASSWORD }}
    steps:
      - uses: actions/checkout@v7
      - uses: actions/setup-python@v7
        with:
          python-version: "3.12"
      - run: pip install "dbt-core~=1.12.0" "dbt-postgres~=1.11.0"
      - run: dbt deps
      - run: dbt docs generate --target prod --profiles-dir .
      - run: |
          mkdir -p site
          cp target/index.html target/manifest.json target/catalog.json site/
      - uses: actions/upload-pages-artifact@v5
        with:
          path: site
  deploy:
    needs: build
    runs-on: ubuntu-latest
    environment:
      name: github-pages
      url: ${{ steps.deployment.outputs.page_url }}
    steps:
      - id: deployment
        uses: actions/deploy-pages@v5
```

リポジトリの設定でPagesの公開元を「GitHub Actions」にしてから流します。アクションの版は2026年11月11日時点の最新リリースに合わせました。DWHの資格情報は`DBT_ENV_SECRET_`で始まる環境変数で渡し、ログに出ても伏せ字になるようにしています。

### Pagesを社外に見せない条件とS3・CloudFrontでの配信の分かれ目

GitHub Pagesの既定は全公開です。[Pagesの公開範囲の変更](https://docs.github.com/en/enterprise-cloud@latest/pages/getting-started-with-github-pages/changing-the-visibility-of-your-github-pages-site)によると、閲覧をリポジトリの読み取り権限を持つ人に限れるのは、GitHub Enterprise Cloudの組織が所有するprivateかinternalのリポジトリだけです。FreeやTeamのプランで前節のワークフローを流すと、テーブル定義が誰でも読める状態で公開されます。

Enterprise Cloudが無いなら、非公開のS3バケットに置き、CloudFrontのオリジンアクセスコントロール（OAC）経由でだけ読ませます。[Restrict access to an Amazon S3 origin](https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/private-content-restricting-access-to-s3.html)のバケットポリシーと、更新時のコマンドは次の形です。

```
# バケットポリシー（CloudFrontのディストリビューションからの読み取りだけを許可）
{
  "Version": "2012-10-17",
  "Statement": [{
    "Effect": "Allow",
    "Principal": {"Service": "cloudfront.amazonaws.com"},
    "Action": "s3:GetObject",
    "Resource": "arn:aws:s3:::example-dbt-docs/*",
    "Condition": {"StringEquals": {
      "AWS:SourceArn": "arn:aws:cloudfront::111122223333:distribution/EDFDVBD6EXAMPLE"
    }}
  }]
}

# docsの更新（CIの最後に実行）
aws s3 sync site/ s3://example-dbt-docs/ --delete
aws cloudfront create-invalidation --distribution-id EDFDVBD6EXAMPLE --paths "/*"
```

OACはバケットへの直アクセスを塞ぐだけで、CloudFrontのURLを知っていれば誰でも開けます。閲覧者を絞るには、AWS WAFで社内の送信元IPだけを許可するか、社内のIDプロバイダーと連携した認証を前段に置きます。どちらを選ぶかは閲覧者が社外から接続するかで決まり、在宅勤務の閲覧者がいるならIP制限では足りません。

## dbt docsの自前公開を続ける条件とCatalogやデータカタログへ移る判断

公開の仕組みを作ったあとで、残るのは誰が保守するかです。静的サイトのまま続けるか、別の仕組みへ移るかをここで決めます。

### 静的サイトで足りる規模と閲覧専用シートのCatalogを選ぶ場面

自前公開で足りるのは、閲覧者がdbtを書くエンジニアとアナリスト中心で、CIの保守を引き受ける人が1人以上いる場合です。上のワークフローを置けば、追加の費用はDWHへのメタデータ問い合わせと配信費だけで済みます。

事業部門の担当者まで閲覧者に含めるなら、自前公開は勧めません。認証基盤との連携、アクセス権の棚卸し、更新が止まったときの監視まで自分たちの管理範囲になるためです。dbt platformのStarter・Enterprise・Enterprise+では、ジョブの実行ごとにCatalogが自動で更新され、閲覧専用シートを必要な数だけ足せます。費用の見積もりは[dbt 料金の全体像](https://www.issoh.co.jp/column/details/19497/)が試算の参考です。docsの公開を含めたデータ基盤の設計と運用を任せたい場合は、一創の[データ分析基盤構築・MLOps構築支援](https://www.issoh.co.jp/service/ai/data-platform/)でご相談を受けています。

### v2のDocs v2を閉域網で使えない理由とOpenMetadataへ移る条件

Docs v2には見落としやすい前提があります。[View documentation](https://docs.getdbt.com/docs/build/view-documentation)によると、ブラウザは実行時にDuckDB-WASMをCDNから読み込むため、閲覧者の端末にはCDNへの外向き通信が要ります。インターネットへ出られない閉域網の端末では、静的ファイルを社内に置いても表示できません。その環境ではv1のDocsを使い続けるのが現実的です。

dbt以外のデータソース、たとえば業務システムのDBやBIのダッシュボードまで1か所で探したくなったら、dbt docsの守備範囲を超える要件です。[OpenMetadataの構成と導入手順](https://www.issoh.co.jp/tech/details/16132/)のようなデータカタログ製品へ移り、dbtはmanifest.jsonとcatalog.jsonを取り込ませる側に回ります。データカタログを入れるかどうかの判断は[データカタログとは](https://www.issoh.co.jp/column/details/13792/)で整理しています。

## よくある質問

dbt docsを使い始めるときによく聞かれる質問に答えます。

### dbt docsは無料で使えますか？

無料です。dbt-core 1.12系のDocs v1も、dbt v2のDocs v2も、ローカルでの生成と自前の公開に費用はかかりません。かかるのは、`catalog.json`を作るときにDWHへ投げるメタデータ問い合わせの料金と、配信先のS3やCloudFrontの利用料です。dbt platformのCatalogで共有する場合は、Starter以上のプランの契約が要ります。

### dbt docs serveで社内に公開してもよいですか？

勧めません。公式ドキュメントは`dbt docs serve`をローカルの開発用途に限っており、1.12系の実装はPython標準のHTTPサーバーで認証もHTTPSもありません。チームに見せるなら、生成したファイルをGitHub Pages（Enterprise Cloudで非公開設定）か、S3とCloudFrontのような認証を掛けられる配信先に置いてください。

### dbt docsのリネージに列単位の依存は出せますか？

dbt v2のDocs v2なら出せます。`dbt build --generate-info-schema --static-analysis strict`でビルドしてから、`dbt docs generate --no-compile`でサイトを作ります。dbt-core 1.12系のDocs v1が表示するのはモデル単位のリネージだけです。列単位の追跡が必要でv2へ移れない場合は、dbt platformのCatalogかデータカタログ製品を検討します。

### dbt docs generateが遅いときはどうすればよいですか？

遅いのは多くの場合、DWHへのメタデータ問い合わせです。`--select`で対象を100ノード未満に絞るとWHERE句付きの問い合わせになり、DWH側で絞り込まれます。開発中にリネージだけ見たいなら`--empty-catalog`で問い合わせ自体を省けます。直前にコンパイル済みなら`--no-compile`も併用してください。

### dbt docsとdbt Catalogの違いは何ですか？

dbt docsは自分で生成して配信する静的サイトで、dbt CoreでもdbtのDeveloperプランでも使えます。Catalogはdbt platformのStarter以上のプランに含まれ、ジョブの実行ごとに自動で更新されるうえ、実行結果や利用状況も見られる点が違いです。dbt CoreとCloud（dbt platform）のどちらを選ぶかの判断軸は[dbtとは：dbt Core・Cloudの選び方](https://www.issoh.co.jp/column/details/16548/)で整理しています。

## 関連記事

- [dbtとは？ELTのTを担う仕組みとdbt Core・Cloudの選び方【2026年版】](https://www.issoh.co.jp/column/details/16548/)：dbtの仕組みと採用判断
- [dbt Coreの使い方：インストールからprofiles.yml・dbt build・CIまでの手順【1.12対応】](https://www.issoh.co.jp/tech/details/19592/)：docsの前提になる環境構築
- [dbt Semantic Layerの使い方：設定からJDBC・GraphQL・Python SDKで指標を引くまで【2026年版】](https://www.issoh.co.jp/tech/details/19595/)：Docs v2に表示される指標定義の書き方
- [dbtのmarts層とは？3層の分け方とMetricFlowで指標を定義する手順【dbt 1.12対応】](https://www.issoh.co.jp/tech/details/12323/)：リネージを読みやすくするレイヤ設計
- [DuckDBの使い方：インストールからCLI・Python・ファイル読み込みまでの手順【1.5.6対応】](https://www.issoh.co.jp/tech/details/15377/)：Docs v2の索引を読むDuckDB自体の操作

---

出典: [dbt docsの使い方：generate・serveでリネージを作り社内に公開する手順【v2対応】](<https://www.issoh.co.jp/tech/details/19599/>)（株式会社一創）
