| /** |
| * @fileoverview NodeJS binding to run the buildozer command through a convenient API |
| */ |
| const {spawnSync} = require('node:child_process'); |
| // bazel will copy the /launcher.js in this repo while building the package |
| const {getNativeBinary} = require('./buildozer'); |
| |
| /** |
| * run buildozer with a list of commands |
| * @see https://github.com/bazelbuild/buildtools/tree/main/buildozer#do-multiple-changes-at-once |
| * @returns The standard out of the buildozer command, split by lines |
| */ |
| function run(...commands) { |
| return runWithOptions(commands, {}); |
| } |
| |
| /** |
| * run buildozer with a list of commands |
| * @param commands a list of CommandBatch to pass to buildozer |
| * @param options Options to pass to spawn |
| * @param flags any buildozer flags to pass |
| */ |
| function runWithOptions(commands, options, flags = []) { |
| // From https://github.com/bazelbuild/buildtools/tree/main/buildozer#usage: |
| // Here, label-list is a space-separated list of Bazel labels, |
| // for example //path/to/pkg1:rule1 //path/to/pkg2:rule2. |
| // Buildozer reads commands from FILE (- for stdin |
| // (format: |-separated command line arguments to buildozer, excluding flags)) |
| const input = commands.map(c => [...c.commands, c.targets.join(',')].join('|')).join('\n'); |
| const {stdout, stderr, status, error} = spawnSync(getNativeBinary(), flags.concat([ |
| '-f', '-' /* read commands from stdin */ |
| ]), { |
| ...options, |
| input, |
| encoding: 'utf-8', |
| }); |
| // https://github.com/bazelbuild/buildtools/tree/main/buildozer#error-code |
| if (status == 0 || status == 3) return stdout.trim().split('\n').filter(l => !!l); |
| |
| console.error(`buildozer exited with status ${status}\n${stderr}`); |
| throw error; |
| } |
| |
| module.exports = { |
| runWithOptions, |
| run, |
| }; |