天天看點

Bazel - 6(外部Bazel項目依賴 - local_repository)

作者:心動不凍

前面的例子都是在同一個repository裡面折騰,現在是時候出去透透氣了。外面已經有了那麼多優秀的開源項目,千萬不要重複造輪子,再說咱也造不過來呀。

将外部項目作為依賴引入是必需的。這些項目有些是Bazel項目,裡面有WORKSPACE,有BUILD,定義了若幹targets。但也有些并不是Bazel項目。對于前者,按照這些項目的存放地點不同,分為local_repository,git_repository,http_archive。對于後者,指定它們隻需要加一個new的字首,即new_local_repository,new_git_repository,new_http_archive。

我們先介紹第一個,local_repository,即本地檔案系統中的Bazel項目。

這回我們需要建立兩個repository,hello-world-lib實作功能函數,hello-world-main調用函數。

hello-world-lib目錄結構如下

Bazel - 6(外部Bazel項目依賴 - local_repository)

為了不讓目錄太過瑣碎,我直接在repository的根目錄放置了一個BUILD,使其成為一個package。BUILD内容如下

load("@rules_cc//cc:defs.bzl", "cc_library")

cc_library(
    name = "hello-world-lib",
    srcs = ["src/hello-world.cc"],
    hdrs = ["include/hello-world.h"],
    visibility = ["//visibility:public"],
)           

include/hello-world.h

#pragma once

#include <string>

std::string hello_world();           

src/hello-world.cc

#include "include/hello-world.h"

std::string hello_world() { return "Hello, world!"; }           

下面開始做第二個repository,hello-world-main,這次有點新東西,那個一直為空的WORKSPACE這回要派上用場了。它的主要用途就是将項目中用到的外部依賴引入進來,提供給相應的targets使用。

Bazel - 6(外部Bazel項目依賴 - local_repository)

WORKSPACE内容如下

local_repository(
    name = "hello-world-lib",
    path = "../hello-world-lib",
)           

local_repository告訴Bazel我要引入一個外部Bazel項目,我給它起個名字叫hello-world-lib,它位于本機檔案系統,在上層目錄的hello-world-lib目錄中(也可以使用/path/to/repo-name這樣的絕對路徑)。

src/BUILD

load("@rules_cc//cc:defs.bzl", "cc_binary")

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

這回deps中的label使用了完整的形式,//之前是repository名,後面是target路徑。由于我們之前把package直接定義在了根目錄,是以這裡沒有package目錄名。

src/hello-world-main.cc

#include "include/hello-world.h"
#include <iostream>

int main() {
  std::cout << hello_world() << std::endl;
  return 0;
}           

注意include的路徑,是從repository的根目錄開始的。

編譯運作,成功!

Bazel - 6(外部Bazel項目依賴 - local_repository)

源碼擷取:[email protected]:zhouxindong/bazel-learning.git