Often needed little bits of bazel knowledge that I tend to forget.
Module extensions
Reminder about module extensions.
# Also instead of `http.bzl`, `git.bzl` etc.
http_file = use_repo_rule("@bazel_tools//tools/build_defs/repo:http.bzl", "http_file")
http_file(
name = "data_file",
url = "http://example.com/file",
sha256 = "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",
)
Print errors inline
By default bazel prints the path to error logs. In development it is often more useful to see the error printed right away.
bazel test --test_output=errors //...
You can add:
test --test_output=errors
into your $HOME/.bazelrc as well.
Print only errors
By default bazel prints the status of passing tests. This causes bazel to print details about failing tests only.
bazel test --test_summary=terse
You can add:
test --test_summary=terse
into your $HOME/.bazelrc as well.
Override a repository with a command line flag
build --override_repository=com_google_protobuf=/abs/path/to/repo
This allows you to use an alternate source repository from the one declared in WORKSPACE, or worse, in dependencies. You can use that to generate a quick patch, or to provide a fix to upstream.
When co-developing workspaces, you can put the above line in your .bazelrc file, so that you do not need to add it into every command line.
Override a module
This is similar to the above advice, except for modules. --override_repository does not work for modules, even if you can find an incantation which would be valid with the new canonical repository naming.
Use instead a different flag, --override_module=... which has a syntax similar to --override_repository. Except, when overriding a module, you can use the apparent module name normally.
User bazelrc
in .bazelrc:
try-import %workspace%/user.bazelrc
Then create user.bazelrc in your workspace root and add it to .gitignore if you use git, so that it remains unique to you.
But, don’t forget that you have it.
Use rules_rust
Not sure why, but various bazel rules don’t seem to be documented well. While there are examples, there’s minimal explanation on how rules work. And the way rules work changes substantially across rules releases.
To fix this, I made a small but complete example of using rules_rust and its IDE integration via rust-project.json.
See it at: http://github.com/filmil/rust-bazel-example, refer to README.md for details.
Expand locations in a build rule
ctx.expand_location(val, ctx.attr.deps)
This expands any appearances of $(location <label>) in deps.
Examples of some of the above https://github.com/filmil/bazel-bats/blob/main/rules.bzl#L69
Template expansion
Generate a file based on a template.
Example: https://github.com/bazelbuild/examples/blob/main/rules/expand_template/hello.bzl
Release an archive with GitHub actions and Bazel
Here’s an example: https://github.com/filmil/bazoekt/blob/main/.github/workflows/release.yml
Packaging
Here is how to make a distribution zip archive.
With: https://github.com/bazelbuild/rules_pkg/tree/main/examples/rich_structure
pkg_files(
name = "share_doc",
srcs = [
"//docs",
],
# Where it should be in the final package
prefix = "usr/share/doc/foo",
# Required, but why?: see #354
strip_prefix = strip_prefix.from_pkg(),
)
pkg_filegroup(
name = "manpages",
srcs = [
"//src/client:manpages",
"//src/server:manpages",
],
prefix = "/usr/share",
)
pkg_tar(
name = "foo_tar",
srcs = [
"README.txt",
":manpages",
":share_doc",
"//resources/l10n:all",
"//src/client:arch",
"//src/server:arch",
],
)
pkg_zip(
name = "foo_zip",
srcs = [
"README.txt",
":manpages",
":share_doc",
"//resources/l10n:all",
"//src/client:arch",
"//src/server:arch",
],
)
Specifying your own registry
Bazel registries are a new concept from the world of bazel’s bzlmod. If you have projects that do not live in bazel’s central registry at https://bcr.bazel.build, you can do this instead. I add a new registry that contains my projects. When you use the --registry flag, the default BCR registry is lost, so you have to insert it again. You may want to reverse the order of registries to ensure that BCR definition have precedence.
common --registry=https://raw.githubusercontent.com/filmil/bazel-registry/main
common --registry=https://bcr.bazel.build