By Alex, Alibaba Cloud Community Blog author
For developing an application, developers use their machine that runs OS X, Windows or Linux. At the same time, they use a foreign platform such as Alibaba Cloud's ECS instances installed with Ubuntu or CentOS or another platform for testing. Therefore, there is a great need for the capability that uses a single system to compile binaries that run across multiple platforms. Golang offers a solution to the problem. It allows developers to design systems that run across diverse platforms. Also known as cross-compiling, Golang offers a tremendous advantage to cross-platform developers. The language has many built-in features to support development across platforms. This article explores how to use such solutions for making the development process less strenuous, what are the best practices, and how Golang facilitates testing out new solutions and package distribution.
To begin with, let's take a quick look at the key best practices for implementing cross-compilation.
To meet the interface requirements on Go, every object must ensure the implementation of all defined methods. This may result in the distinct implementation of two objects from different platforms but still meeting the requirements of Go interfaces. It is advisable to abstract all platform-specifics behind Go interfaces.
The build constraints on Go control a compiled file's platform using language constructs. They are of two types:
Use the GOOS and GOARCH values in the runtime package to get the OS and architecture information at runtime. Next, compare those using standard conditionals with the values that are already known. Nonetheless, runtime checking is not useful most of the time as it increases the chances of encountering errors.
You need the following essentials to work through the tutorial.
Compile the executables for specific target operating systems (OS) such as Darwin/amd64 and Linux/amd64 and build these executables in a local machine (for this tutorial, MacBook). Export the executables to the GitHub account and clone to the Ubuntu server hosted by Alibaba Cloud.
For a local Mac machine, build the executables for the Darwin/amd64 target. Once, the Go is installed, run the commands below.
cd src
GOOS=darwin GOARCH=amd64 CGO_ENABLED=1 ./make.bash ¨Cno-clean
Following is the anticipated response from the preceding command.
Installed Go for darwin/amd64 in /Users/name/go
Installed commands in /Users/name/go/bin
The command creates all libraries and tools in the go, godoc and, gofmt directories. Run the command below to create a PATH for the tools.
export PATH=$HOME/go/bin:$PATH
Now check the Go environment using the following commands.
go env
GOARCH="amd64"
GOBIN=""
GOCHAR="6"
GOEXE=""
GOHOSTARCH="amd64"
GOHOSTOS="darwin"
GOOS="linux"
GOPATH=""
GORACE=""
GOROOT="/Users/name/go"
GOTOOLDIR="/Users/name/go/pkg/tool/darwin_amd64"
CC="gcc"
GOGCCFLAGS="-g -O2 -fPIC -m64"
CGO_ENABLED="1"
Run the command below to check the Go version.
go version
go version go1.12.1 darwin/amd64
Anticipated Errors: To solve the following anticipated errors while setting up the Go target, refer to this guide.
crypto/x509 root_darwin.go:9:43: error:
CoreFoundation/CoreFoundation.h:
root_darwin.go:10:31: error: Security/Security.h:
Open the Go directory to view all the required tools to build the Go programs. For this tutorial, it shows the darwin_amd64
folder for Mac.
For this step, compile an executable file to run on Linux/amd64. To start, run the command below.
GOOS=linux GOARCH=amd64 CGO_ENABLED=0 ./make.bash ¨Cno-clean
Set CGO_ENABLED
to 0 to implement cross-compiling and get the following output.
Installed Go for linux/amd64 in /Users/name/go
Installed commands in /Users/name/go/bin
Now, you'll get new folders for Linux/amd64 in the bin and PKG directories.
Refer to the following table to choose a target OS:
$GOOS | $GOARCH | |
darwin | 386 | 32-bit MacOSX |
darwin | amd64 | 64-bit MacOSX |
freebsd | 386 | |
freebsd | amd64 | |
linux | 386 | 32 bit Linux |
linux | amd64 | 64 bit Linux |
linux | arm | RISC Linux |
netbsd | 386 | |
netbsd | amd64 | |
openbsd | 386 | |
openbsd | amd64 | |
plan9 | 386 | |
windows | 386 | 32 bit Windows |
windows | amd64 | 64 bit Windows |
Now, execute the following commands to build the programs to run on Linux and Ubuntu.
cd $HOME
mkdir example
Setup a GOPATH as shown below:
export GOPATH=$HOME/example
cd example
mkdir src
cd src
mkdir simple
cd example/src/simple
Next, create a new file named main.go
in the directory with the following content.
package main
import (
"fmt"
)
func main() {
fmt.Println("Hello World!")
}
Build a Linux/amd64 executable by running the command below in the terminal:
export GOARCH="amd64"
export GOOS="linux"
go build
file simple
Simple: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), statically linked, not stripped
Run the following command in the terminal to build a darwin/amd64 executable.
go build
file simple
simple: Mach-O 64-bit executable x86_64
Choose a different platform and architecture by changing the OS/ARCH variables in the command. Once the build is complete, obtain an executable that is compatible with the target OS/ARCH variables.
Deploying executables for multiple platforms is an extremely slow and time-consuming process. Let's write a program that will help us automate the process. The script shall have operating systems and platform pairs to generate executables in a directory.
Alright, let's get started!
Switch to your home directory by executing the following command:
cd ~
Run the command below to create a new bash file named auto-build.bash
.
nano auto-build.bash
To avoid complicating the process, check what the script needs to contain and then compile it swiftly. Once you understand what needs to be done, it is very easy to work with such a script.
First, make the script executable using the following command.
auto-build.bash
#!/usr/bin/env bash
Consider the following requirements for the script:
$package
variable's value.$package_split
array.Based on the above requirements, refer to the following script:
auto-build.bash
#!/usr/bin/env bash
package=$1
if [[ -z "$package" ]]; then
echo "usage: $0 <package-name>"
exit 1
fi
package_split=(${package//\// })
package_name=${package_split[-1]}
platforms=("windows/amd64" "windows/386" "linux/amd64" "linux/386")
for platform in "${platforms[@]}"
do
platform_split=(${platform//\// })
GOOS=${platform_split[0]}
GOARCH=${platform_split[1]}
output_name=$package_name'-'$GOOS'-'$GOARCH
if [ $GOOS = "windows" ]; then
output_name+='.exe'
fi
env GOOS=$GOOS GOARCH=$GOARCH go build -o $output_name $package
if [ $? -ne 0 ]; then
echo 'We have encountered an error while executing! Aborting the process...'
exit 1
fi
done
The above script allows building executables for Windows 64-bit, 32-bit, Linux 64-bit, and Linux 32-bit. There are many ways of creating a script, but the variables and methods remain more or less the same. Now, run the following command to make it executable.
- chmod +x auto-build.bash
There you go! Now the process of compiling executables is automated and can be run using the command below.
./auto-build.bash $GOPATH/
Since there is no output for the completed processes, use the IS command to determine whether the executables are created successfully. Use any combination of operating systems and architectures with the platforms variable.
After building the Go programs for the chosen platforms and architectures, install the Go tools by executing the following commands.
go get golang.org/x/tools/cmd/godoc
go get golang.org/x/tools/cmd/vet
go get golang.org/x/tools/cmd/goimports
go get golang.org/x/tools/cmd/gorename
go get golang.org/x/tools/cmd/oracle
go get golang.org/x/tools/cmd/gotype
go get github.com/golang/lint/golint
This tutorial describes how developers must use Go to deal with packages and cross-compile executables for different target platforms. It suggests how to use a simple script to automate the compilation process for Linux and Windows to save time and increase efficiency. Refer to the Go document for comprehensive information about how to build Go executables from the source. Also, use a tool called gox to build executables for various platforms with minimal requirements. Now, without much ado subscribe to Alibaba Cloud ECS and get started with the lessons.
Don't have an Alibaba Cloud account? Sign up for an account and try over 40 products for free worth up to $1200. Get Started with Alibaba Cloud to learn more.
Alibaba Cloud Native - October 11, 2024
Alibaba Cloud Native Community - October 15, 2024
Alibaba Cloud Native Community - March 14, 2023
Alibaba Cloud Community - June 27, 2023
Alibaba Container Service - April 28, 2020
Alibaba Cloud Native Community - December 30, 2021
Conduct large-scale data warehousing with MaxCompute
Learn MoreProvides a control plane to allow users to manage Kubernetes clusters that run based on different infrastructure resources
Learn MoreA secure image hosting platform providing containerized image lifecycle management
Learn MoreElastic and secure virtual cloud servers to cater all your cloud hosting needs.
Learn MoreMore Posts by Alex