bazel

Practical Bazel: Supporting Trinary Stamp Attributes
Practical Bazel bazel stamping
Published: 2023-03-06
Practical Bazel: Supporting Trinary Stamp Attributes

In Bazel, stamping is the process of embedding additional information into built binaries, such as the source control revision or other workspace-related information. Rules that support stamping typically include an integer stamp attribute, where 1 means “always stamp”, 0 means “never stamp”, and -1 means “use the Bazel build --stamp flag. This blog post explains how to write a rule that supports these values.

Read more...
Practical Bazel: local_archive() Workspace Rule
Practical Bazel bazel
Published: 2023-03-01
Practical Bazel: local_archive() Workspace Rule

In general, one should never check in binary artifacts into Git; it is better to retrieve them from an artifact repository or a website using http_archive(). However, sometimes convenience is more important than ideological purity. To handle these cases, I wrote a simple workspace rule named local_archive().

Read more...
Practical Bazel: Building Multiple Workspaces in CI
Practical Bazel bazel
Published: 2022-10-18
Practical Bazel: Building Multiple Workspaces in CI

For most Bazel projects, I strongly recommend using a single Bazel workspace per source code repository. However, it can be occasionally useful to nest multiple workspaces within a single repository. For example, when I’m writing Bazel rulesets, I will often create test cases that contain own workspace with a slightly different configuration in order to test various workspace-level configuration settings for the ruleset, while maintaining a root workspace which is the primary workspace for the ruleset.

Read more...
Practical Bazel: Use a Single .bazelrc With Multiple Configurations
Practical Bazel bazel
Published: 2022-10-17
Practical Bazel: Use a Single .bazelrc With Multiple Configurations

Bazel users commonly need to manage multiple different configurations when building and testing software, such as:

  • A configuration that is used by developers on their own PCs, which often has debug mode turned on
  • A configuration that is used by the continuous integration (CI) default build and test pipeline, which often builds in release mode
  • A configuration for generating a tagged, version release, which often has stamping enabled
  • (Perhaps many more)
Read more...
Practical Bazel: Implementing compilation_mode in Rules
Practical Bazel bazel
Published: 2022-10-13
Practical Bazel: Implementing compilation_mode in Rules

As developers know, virtually all compilers support the notion of compilation mode, e.g.. whether to compile the code in debug or release mode. In Bazel, this concept is built natively into the build system itself. When compiling software using bazel build, one can select a compilation mode using the --compilation_mode (often shorted to -c) flag.

Read more...
Practical Bazel: A Starting CI Pipeline
Practical Bazel bazel continuous-integration
Published: 2021-09-14
Practical Bazel: A Starting CI Pipeline

This post describes a pattern for implementing a continuous integration (CI) pipeline using Bazel. This pattern is my starting point whenever I set up a new Bazel-based project in CI, after which I add any project-specific pipeline customizations.

This pipeline is purely about the CI (build to release) stages of a pipeline. A full continuous delivery (CD) pipeline, which includes deployment, will be discussed in a later post.

Read more...
Practical Bazel: A Simpler Way to Wrap Run Targets
Practical Bazel bazel
Published: 2020-11-20
Practical Bazel: A Simpler Way to Wrap Run Targets

Yesterday, I explained how you can wrap a bazel run target with a sh_binary() to execute arbitrary code both before and after the run target, which is particularly useful for retrieving secrets from a secret management system and passing them to the run target.

If you are passing secrets via environment variables that are retrieved by command-line programs, there’s an even easier way to do it – use the command rule from Atlassian’s bazel-tools repo and its raw_environment attribute.

Read more...
Practical Bazel: Wrapping Run Targets to Provide Additional Context
Practical Bazel bazel
Published: 2020-11-19
Practical Bazel: Wrapping Run Targets to Provide Additional Context

An executable rule which can be executed via bazel run is the natural way to model interactions with external systems in Bazel such as uploading build artifacts to a remote artifact repository. For example, imagine a rules_artifactory ruleset which includes a rule artifactory_push() executable rule which uploads a compiled .dpkg to an Artifactory apt repository, or a rules_docker ruleset which has a rule docker_push() which pushes a Docker image to a remote image repository.

Read more...
Practical Bazel: Changing Behavior on Windows
Practical Bazel bazel windows
Published: 2020-11-05
Practical Bazel: Changing Behavior on Windows

Bazel started on Linux and Mac OS, and most people use Bazel on these platforms exclusively, but Bazel can execute on Windows as well. However, Windows has enough idiosynchatic differences that writing a single, operating-system agnostic rule that executes on both Windows and Linux/Mac is quite hard. Often it is easiest to have the rule detect whether it is running on Windows and execute different behavior.

Read more...
Practical Bazel: Excluding Part of Tree
Practical Bazel bazel
Published: 2020-10-28
Practical Bazel: Excluding Part of Tree
Quick Bazel tip for today: If you want to build everything except for a specific subtree, you can prefix the subtree you want to exclude with a -. For example, to build everything except for //client_access_library/...: bazel build -- //... -//client_access_library/...
Practical Bazel: Use a Specific Version of Bazel
Practical Bazel bazel bazelisk
Published: 2020-10-27
Practical Bazel: Use a Specific Version of Bazel
Bazel’s philosophy strongly encourages binding to exact, specific versions of all third-party dependencies to help ensure reproducible builds. As Bazel users, we must remember to extend this philosophy to Bazel itself. When setting up a Bazel-based build system, you should choose a specific version of Bazel and require all developers and the build system to use it. This can be done in a few ways: Use Bazelisk and a . Read more...
Practical Bazel: path or short_path?
Practical Bazel bazel
Published: 2020-10-22
Practical Bazel: path or short_path?
When writing custom Bazel rules, you spend a lot of time either reading or writing Bazel File objects. File objects have two properties for accessing the underlying file path: File.path and File.short_path. When writing custom rules, I often chose one of the two properties at random, and switched to the other if it didn’t work right. I wrote some simple custom rules to test the various combination of rule types and file types to determine when I should use path or short_path. Read more...
Practical Bazel: Start with Genrules
Practical Bazel bazel libpng autoconf make
Published: 2020-10-21
Practical Bazel: Start with Genrules
Bazel is a powerful yet complicated system, and it can be intimidating to newcomers. While the Bazel user guide and user manual preach the benefits of giving Bazel full control over your build process by rewriting all build processes using Bazel-native rulesets (as Google reportedly does internally), this is an immense amount of work. Specifically, if you are integrating third-party software into your Bazel-based build process, reverse engineering and rewriting the third-party project’s build system into Bazel can easily take days – and then you need to maintain it. Read more...
Practical Bazel: Introduction
Bazel bazel monorepo continuous-integration continuous-delivery
Published: 2020-10-20
Practical Bazel: Introduction
In 2020, I led the redesign and re-implementation of the object storage system behind RelativityOne. As part of this project we reengineered the continuous delivery pipeline of the service to embrace the philosophy of a service-wide monorepo with a Bazel-based build system. We chose Bazel because we wanted a build system that could support many different languages (the service has code written in C, C#, Python, Go, Terraform, Packer, and other languages…) while remaining fast and correct. Read more...