hedzr/bgo

bgo
provides a super easy way to build your go apps.
All things you need to do is entering the golang project directory and entering bgo
and pressing Enter.
powered by cmdr.

Features
bgo
makes your golang building life easier, it's an efficient and extensible build tool.
-
bgo
or bgo build
: Run go building with or without a config file .bgo.yml
-
bgo run -- ...
: Forward command-line to go run
as is
-
bgo test -- ...
: Forward command-line to go test
as is
-
bgo init
: Scan the directory to grab all main packages and initial .bgo.yml
-
bgo list
: list managed projects in all of .bgo.yaml
-
bgo sbom
: dump #SBOM information itself or specified executables
-
More extensible commands
-
While
-
you have lots of small cli apps in many sub-directories
-
one project wants go1.18beta1 and others stays in go1.17
-
too much -tags
, -ldflags
, -asmflags
, ...
-
multiple targets, cross compiling
-
etc.
have a try with bgo
.
History
-
v0.5.18
- upgrade deps
- fixed: change
SaveAs
(--output
) field from string slice to string
-
v0.5.16
- upgrade deps
- fixed a little
-
More in CHANGELOG
Getting Started
Install
Download the prebuilt binaries from Release page.
Or Built from source code:
go install github.com/hedzr/bgo@latest
bgo --help # -h
bgo --version # -V
bgo --build-info # -#
You may clone and compile bgo
from source code:
git clone https://github.com/hedzr/bgo.git
cd bgo
go run . -s
go run . -s
will run bgo from source code and install itself to ~/go/bin/.

You could run bgo via docker way:
docker pull hedzr/bgo
# or
docker pull ghcr.io/hedzr/bgo:latest
And run it:
docker run -it --rm -v $PWD:/app -v /tmp:/tmp -v /tmp/go-pkg:/go/pkg hedzr/bgo
For macOS/Linux, there is a brew formula:
brew install hedzr/brew/bgo
Run directly
To work without .bgo.yml
, simply go into a folder and run bgo, the cli apps under the folder will be found out and built.
cd my-projects
bgo # start `bgo` in auto mode, see Scopes chapter below

Filter the target systems by -for OS/ARCH
, -os OS
and -arch ARCH
:
bgo --for linux/386 -for linux/amd64,darwin/arm64
bgo -os linux -arch 386 -arch amd64 -arch arm64
Both long and short options are available for for
, os
and arch
.
Their values are stacked by specifying multiple times, so -arch 386 -arch amd64 -arch arm64
is same with --arch 386,amd64,arm64
.
Run with .bgo.yml
Create .bgo.yml
at first
cd my-projects
bgo init # create bgo.yml by scanning
mv bgo.yml .bgo.yml # rename it
Tune .bgo.yml
See sample of .bgo.yml
.bgo.yml
Run
bgo
bgo will load projects from .bgo.yml
and build them
Scopes
bgo -s
: short mode - this will build first project with current GOOS/GOARCH.
bgo
|bgo -a
: auto mode - build projects in .bgo.yml
bgo -f
: full mode - build by scanning current directory
Using shell auto-completion
Run bgo gen sh --zsh
to install auto-completion script to the proper location and enable the feature:

For macOS, you may install zsh completion script manually (not recommended, the better way is by HomeBrew):
bgo gen sh --zsh --output "$(brew --prefix)/share/zsh/site-functions/_bgo"
Run bgo gen sh --bash -o=bgo.bash
to get bash completions script and put it to the right location. Generally it should be:
bgo generate shell --bash -o=bgo.bash
mv bgo.bash /etc/bash-completion.d/bgo
Nothing needs to do if installed via brew (since v0.3.3+).
Others Subcommands
run
bgo run
can forward arguments to go run
. For the command line
bgo run -- ./...
The underlying real command will be run:
go run ./...
test
bgo test
can forward arguments to go test
. For the command line
bgo test -- ./...
The underlying real command will be run:
go test ./...
SBOM
Checking executable's SBOM (Software Bill Of Materials
) without golang installed:
bgo sbom # show sbom of bgo itself
# Show these executables
bgo sbom ~/go/bin/gopls ~/go/bin/golangci-lint
Extensible Commands
The commands system of bgo
can be extensible by editing .bgo.yaml
.
Config Files of bgo
bgo
loads all bgo.yaml
as its configurations from these locations:
- Main Config Files:
/etc/bgo/bgo.yml
and conf.d/*.yml
in it
/usr/local/etc/bgo/bgo.yml
and conf.d/*.yml
in it
Any of them will be loaded as default config set.
- Secondary Config Files:
$HOME/.bgo/bgo.yml
and conf.d/*.yml
in it
$HOME/.config/bgo/bgo.yml
and conf.d/*.yml
in it
Any of them will be loaded as extensible config set.
- Alternative Config File:
./.bgo.yaml
This config file is used to current building project by bgo
.
The scanning results of golang CLI apps from current directory will be written into this file.
Customize the extensible commands in Main/Secondary Config Files
The extensible commands from config file is a feature of hedzr/cmdr
. It generally looks like:
Expand to source codes of `80.aliases.yml`
# ~/.config/bgo/conf.d/80.aliases.yml
app:
aliases:
# group: # group-name (optional). such as: "别名".
commands:
# - title: list
# short-name: ls
# # aliases: []
# # name: ""
# invoke-sh: ls -la -G # for macOS, -G = --color; for linux: -G = --no-group
# # invoke: "another cmdr command"
# # invoke-proc: "..." # same with invoke-sh
# desc: list the current directory
# - title: echo
# invoke-sh: |
# # pwd
# echo "{{$flg := index .Cmd.Flags 0}}{{$path :=$flg.GetDottedNamePath}} {{$fullpath := .Store.Wrap $path}} {{$fullpath}} | {{.Store.GetString $fullpath}}"
# desc: print the name
# flags:
# - title: name
# default: # default value
# type: string # bool, string, duration, int, uint, ...
# group:
# toggle-group:
# desc: specify the name to be printed
- title: check-code-qualities
short-name: chk
# aliases: [check]
# name: ""
invoke-sh: |
which golint || go install golang.org/x/lint/golint
which gocyclo || go install github.com/fzipp/gocyclo
echo
echo
echo "Command hit: {{.Cmd.GetDottedNamePath}}"
echo "fmt {{.ArgsString}} ..."
gofmt -l -s -w {{range .Args}}{{.}}{{end}}
echo "lint {{.ArgsString}} ..."
golint {{.ArgsString}}
echo "cyclo ."
gocyclo -top 13 .
# invoke: "another cmdr command"
# invoke-proc: "..." # same with invoke-sh
shell: /usr/bin/env bash # optional, default is /bin/bash
desc: pre-options before releasing. typically fmt,lint,cyclo,...
- title: coverage
short-name: cov
invoke-sh: |
# pwd
# echo "{{$flg := index .Cmd.Flags 0}}{{$path := $flg.GetDottedNamePath}} {{$fullpath := .Store.Wrap $path}} {{$fullpath}} | {{.Store.GetString $fullpath}}"
# echo "{{$flg = index .Cmd.Flags 1}}{{$path = $flg.GetDottedNamePath}} {{$fullpath2 := .Store.Wrap $path}} {{$fullpath2}} | {{.Store.GetString $fullpath2}}"
# echo "{{$flg = index .Cmd.Flags 2}}{{$path = $flg.GetDottedNamePath}} {{$fullpath3 := .Store.Wrap $path}} {{$fullpath3}} | {{.Store.GetString $fullpath3}}"
go test -v -race \
-coverprofile={{.Store.GetString $fullpath2}} \
-covermode=atomic -timeout=20m \
{{if not .Args}}.{{else}}{{.ArgsString}}{{end}} \
| tee {{.Store.GetString $fullpath3}}
go tool cover \
-html={{.Store.GetString $fullpath2}} \
-o={{.Store.GetString $fullpath}}
desc: run coverage, produce coverage.txt and cover.html
examples: bgo cov ./... or bgo cov
flags:
- title: html
default: cover.html # default value
default-placeholder: FILE
type: string # bool, string, duration, int, uint, ...
group:
toggle-group:
desc: specify the html filename to be output
- title: text
default: coverage.txt # default value
default-placeholder: FILE
type: string # bool, string, duration, int, uint, ...
group:
toggle-group:
desc: specify the coverprofile filename
- title: log
default: coverage.log # default value
default-placeholder: FILE
type: string # bool, string, duration, int, uint, ...
group:
toggle-group:
desc: specify the name to be logged
The config adds two top-level subcommands: chk
(check-code-qualities
) and cov
(coverage
)
Another sample is the bundled 91.more.aliases.yml
:
Expand to source codes of `91.more.aliases.yml`
app:
aliases:
# group: # group-name (optional). such as: "别名".
commands:
# - title: list
# short-name: ls
# # aliases: []
# # name: ""
# invoke-sh: ls -la -G # for macOS, -G = --color; for linux: -G = --no-group
# # invoke: "another cmdr command"
# # invoke-proc: "..." # same with invoke-sh
# desc: list the current directory
- title: yolo
short-name: y
invoke-sh: |
which yolo || { echo "installing yolo..." && go install -v github.com/azer/yolo; }
yolo -i *.go -c 'go build' -a localhost:8080 {{.ArgsString}}
desc: print the name
- title: echo
invoke-sh: |
# pwd
echo "{{$flg := index .Cmd.Flags 0}}{{$path :=$flg.GetDottedNamePath}} {{$fullpath := .Store.Wrap $path}} {{$fullpath}} | {{.Store.GetString $fullpath}}"
desc: print the name
flags:
- title: name
default: # default value
type: string # bool, string, duration, int, uint, ...
group:
toggle-group:
desc: specify the name to be printed
Inspired By
bgo
building subcommand was inspired by many tools:
LICENSE
Apache 2.0