Bazel チュートリアル: C++ プロジェクトをビルドする

<ph type="x-smartling-placeholder"></ph> 問題を報告する <ph type="x-smartling-placeholder"></ph> ソースを表示 夜間 · 7.3 · 7.2 · 7.1 · 7.0 · 6.5

はじめに

Bazel を初めて使用する場合皆さんにおかれましては、この最初の Build チュートリアルでは、 Bazel の使用方法を簡単に説明します。このチュートリアルでは Bazel のコンテキストで使用され、Bazel の基本を説明します。 説明します。まず、必要なツールを用意し、3 つのアプリケーションをビルドして実行します。 複雑さが増す過程で、どのように、またなぜ複雑化するのかを学びます。

Bazel はビルドシステムであり、 は、多言語ビルドをサポートしています。このチュートリアルでは、例として C++ プロジェクトを使用しています 多くの言語に共通する一般的なガイドラインとフローを示します。

完了までの予想時間: 30 分。

前提条件

まず、Bazel をインストールします(まだインストールしていない場合)。 すでにあります。このチュートリアルではソース管理に Git を使用するため、最良の結果を得るには、 Git を使用することもできます。

次に、次のコマンドを実行して、Bazel の GitHub リポジトリからサンプル プロジェクトを取得します。 任意のコマンドライン ツールで次のコマンドを実行します。

git clone https://github.com/bazelbuild/examples

このチュートリアルのサンプル プロジェクトは examples/cpp-tutorial にあります。 されます。

次のような構造になっています。

examples
└── cpp-tutorial
    ├──stage1
    │  ├── main
    │  │   ├── BUILD
    │  │   └── hello-world.cc
    │  └── MODULE.bazel
    ├──stage2
    │  ├── main
    │  │   ├── BUILD
    │  │   ├── hello-world.cc
    │  │   ├── hello-greet.cc
    │  │   └── hello-greet.h
    │  └── MODULE.bazel
    └──stage3
       ├── main
       │   ├── BUILD
       │   ├── hello-world.cc
       │   ├── hello-greet.cc
       │   └── hello-greet.h
       ├── lib
       │   ├── BUILD
       │   ├── hello-time.cc
       │   └── hello-time.h
       └── MODULE.bazel

3 つのファイルセットがあり、このチュートリアルでは、各セットがステージを表しています。 最初のステージでは、1 つのパッケージ内に 1 つのターゲットをビルドします。2 番目の段階では 単一のパッケージからバイナリとライブラリの両方をビルドできます。3 つ目と 3 つ目の 複数のパッケージを使用してプロジェクトをビルドし、 複数のターゲットにできます。

概要: はじめに

Bazel(と Git)をインストールして、このチュートリアルのリポジトリのクローンを作成すると、次のようになります。 Bazel を使用した最初のビルドの基盤を築きました。次に進む セクションでは用語を定義し workspace

スタートガイド

プロジェクトを作成する前に、ワークスペースを設定する必要があります。ワークスペース プロジェクトのソースファイルと Bazel のビルド出力を保持するディレクトリです。 また、次の重要なファイルも含まれています。

  • MODULE.bazel ファイル。ディレクトリとその内容を Bazel ワークスペースであり、プロジェクトのディレクトリのルートに存在します。 構成します。また、外部依存関係もここで指定します。
  • 1 つ以上の BUILD ファイルで Bazel に指示 プロジェクトのさまざまな部分のビルド方法について知ることができます。同じリージョン内のディレクトリを BUILD ファイルを含むワークスペースが package。(パッケージの詳細は 後ほど説明します)。

今後のプロジェクトで、ディレクトリを Bazel ワークスペースとして指定するには、 そのディレクトリにある MODULE.bazel という名前の空のファイルを探します。ここでは、 チュートリアルでは、各ステージに MODULE.bazel ファイルがすでに存在しています。

BUILD ファイルについて

BUILD ファイルには、Bazel に関するさまざまな種類の手順が含まれています。各 BUILD ファイルに 1 つ以上必要です 一連の指示として rule を指定します。 これにより、実行可能なバイナリなど、必要な出力をビルドする方法を Bazel に指示できます。 使用できます。BUILD ファイル内のビルドルールの各インスタンスは、 target を指定し、特定のリソースへの 一連のソースファイルと 依存関係。標的は 他の標的を指しています

cpp-tutorial/stage1/main ディレクトリの BUILD ファイルを確認します。

cc_binary(
    name = "hello-world",
    srcs = ["hello-world.cc"],
)

この例では、hello-world ターゲットが Bazel の組み込みツールをインスタンス化します。 cc_binary ルール。ルール コンテナ イメージから自己完結型の実行可能バイナリをビルドするよう Bazel に指示します hello-world.cc&gt;ソースファイルを指定します。

概要: スタートガイド

いくつかの重要な用語と、Google Cloud の Bazel を使用しています。次のセクションでは、VM のビルドとテストを プロジェクトのステージ 1。

ステージ 1: 単一のターゲット、単一のパッケージ

いよいよプロジェクトの最初の部分をビルドします。なお、 プロジェクトのステージ 1 セクションの構造は次のとおりです。

examples
└── cpp-tutorial
    └──stage1
       ├── main
       │   ├── BUILD
       │   └── hello-world.cc
       └── MODULE.bazel

次のコマンドを実行して cpp-tutorial/stage1 ディレクトリに移動します。

cd cpp-tutorial/stage1

続いて、次のコマンドを実行します。

bazel build //main:hello-world

ターゲット ラベルの //main: 部分は BUILD ファイルの場所です。 (ワークスペースのルートからの相対パス)です。hello-world は、 BUILD ファイル。

Bazel は次のようなコードを生成します。

INFO: Found 1 target...
Target //main:hello-world up-to-date:
  bazel-bin/main/hello-world
INFO: Elapsed time: 2.267s, Critical Path: 0.25s

最初の Bazel ターゲットをビルドできました。Bazel では、ビルドの出力が ワークスペースのルートに bazel-bin ディレクトリを配置します。

次に、新たにビルドされたバイナリをテストします。

bazel-bin/main/hello-world

これにより、「Hello world」が出力されます。表示されます。

以下は、ステージ 1 の依存関係グラフです。

hello-world の依存関係グラフに、単一のソースを持つ単一のターゲットが表示される
表示されます。

まとめ: ステージ 1

最初のビルドが完了したので、次はビルドの仕組みについて 説明します。次の段階では、VM に VM を追加して ターゲットにできます

ステージ 2: 複数のビルド ターゲット

小規模プロジェクトでは 1 つのターゲットで十分ですが、 複数のターゲットやパッケージに分割できます。これにより 増分ビルド(Bazel は変更されたもののみを再ビルド)で、 プロジェクトの複数の部分を一度にビルドすることで、ビルドを一元的に実行できます。このステージでは チュートリアルではターゲットが追加され、次のチュートリアルではパッケージが追加されます。

これは、ステージ 2 で作業するディレクトリです。

    ├──stage2
    │  ├── main
    │  │   ├── BUILD
    │  │   ├── hello-world.cc
    │  │   ├── hello-greet.cc
    │  │   └── hello-greet.h
    │  └── MODULE.bazel

cpp-tutorial/stage2/main ディレクトリの BUILD ファイルを確認します。

cc_library(
    name = "hello-greet",
    srcs = ["hello-greet.cc"],
    hdrs = ["hello-greet.h"],
)

cc_binary(
    name = "hello-world",
    srcs = ["hello-world.cc"],
    deps = [
        ":hello-greet",
    ],
)

この BUILD ファイルを使用して、Bazel はまず hello-greet ライブラリをビルドします( Bazel の組み込み cc_library )、 hello-world バイナリ。hello-world ターゲットの deps 属性は、 hello-world のビルドに hello-greet ライブラリが必要である Bazel バイナリです。

この新しいバージョンのプロジェクトをビルドする前に、 次のコマンドを実行して cpp-tutorial/stage2 ディレクトリに切り替えます。

cd ../stage2

これで、以下の使い慣れたコマンドを使用して新しいバイナリをビルドできるようになりました。

bazel build //main:hello-world

この場合も、Bazel は次のようなコードを生成します。

INFO: Found 1 target...
Target //main:hello-world up-to-date:
  bazel-bin/main/hello-world
INFO: Elapsed time: 2.399s, Critical Path: 0.30s

これで、新たにビルドされたバイナリをテストできるようになりました。これにより、別の「Hello world」が返されます。

bazel-bin/main/hello-world

ここで hello-greet.cc を変更してプロジェクトを再ビルドすると、Bazel のみが そのファイルを再コンパイルします。

依存関係グラフを見ると、hello-worldhello-greet という名前の追加入力:

「hello-world」の依存関係グラフに次の依存関係の変化が表示される
変更が反映されます。

まとめ: ステージ 2

これで、2 つのターゲットを持つプロジェクトがビルドされました。hello-world ターゲットのビルド 1 つのソースファイルで、他の 1 つのターゲット(//main:hello-greet)に依存します。 2 つの追加のソースファイルをビルドします。次のセクションでは、さらに一歩進め 別のパッケージを追加します。

ステージ 3: 複数のパッケージ

次の段階では、さらに複雑な機能を追加してプロジェクトを構築します。 必要があります。次に、Terraform の構造と中身を cpp-tutorial/stage3 ディレクトリ:

└──stage3
   ├── main
   │   ├── BUILD
   │   ├── hello-world.cc
   │   ├── hello-greet.cc
   │   └── hello-greet.h
   ├── lib
   │   ├── BUILD
   │   ├── hello-time.cc
   │   └── hello-time.h
   └── MODULE.bazel

2 つのサブディレクトリがあり、それぞれに BUILD が含まれていることがわかります。 表示されます。したがって、Bazel では、ワークスペースに lib と 2 つのパッケージが含まれるようになりました。 main

lib/BUILD ファイルを確認します。

cc_library(
    name = "hello-time",
    srcs = ["hello-time.cc"],
    hdrs = ["hello-time.h"],
    visibility = ["//main:__pkg__"],
)

main/BUILD ファイルで次のようにします。

cc_library(
    name = "hello-greet",
    srcs = ["hello-greet.cc"],
    hdrs = ["hello-greet.h"],
)

cc_binary(
    name = "hello-world",
    srcs = ["hello-world.cc"],
    deps = [
        ":hello-greet",
        "//lib:hello-time",
    ],
)

メイン パッケージの hello-world ターゲットは hello-time ターゲットによって異なる lib パッケージ内(つまり、ターゲット ラベルは //lib:hello-time)- Bazel は認識しています これは deps 属性で参照できます。これは、依存関係レイヤ 4 に graph:

「hello-world」の依存関係グラフには、メイン パッケージ内のターゲットの状況が表示されます
`lib` 内のターゲットに依存
パッケージ化されています。

ビルドを成功させるには、lib/BUILD//lib:hello-time ターゲットを作成します。 visibility 属性を使用して、main/BUILD のターゲットに明示的に表示できます。 これは、デフォルトではターゲットは、同じリージョン内の他のターゲットにのみ表示されるためです。 BUILD ファイル。Bazel はターゲットの可視性を使用して、ライブラリなどの問題を防止します。 これには、公開 API に漏洩する実装の詳細が含まれます。

プロジェクトのこの最終バージョンをビルドします。cpp-tutorial/stage3 に切り替える 次のコマンドを実行し、

cd  ../stage3

もう一度、次のコマンドを実行します。

bazel build //main:hello-world

Bazel は次のようなコードを生成します。

INFO: Found 1 target...
Target //main:hello-world up-to-date:
  bazel-bin/main/hello-world
INFO: Elapsed time: 0.167s, Critical Path: 0.00s

次に、このチュートリアルの最後のバイナリで、最終的な Hello world メッセージをテストします。

bazel-bin/main/hello-world

まとめ: ステージ 3

これで、プロジェクトを 3 つのターゲットを含む 2 つのパッケージとしてビルドし、 これにより、将来を見据えたソリューションの構築に 紹介しました。次のセクションでは、 Bazel ジャーニー。

次のステップ

これで、Bazel を使用した最初の基本的なビルドが完了しましたが、今回は 開始しますBazel を使用した学習を続けるためのリソースをいくつかご紹介します。

ご利用をお待ちしております。