|
1 | 1 | # golang-with-libgit2
|
2 | 2 |
|
3 |
| -This repository contains a `Dockerfile` which `Makefile` content can be used to build the [libgit2][] dependency |
4 |
| -chain for **AMD64, ARM64 and ARMv7** binaries of Go projects that depend on [git2go][]. |
| 3 | +This repository contains a `Dockerfile` with two files: `Makefile` and `static.sh`. |
| 4 | +Both of which can be used to build the [libgit2][] dependency chain for **AMD64, ARM64 and ARMv7** binaries |
| 5 | +of Go projects that depend on [git2go][]. |
| 6 | + |
| 7 | +The `Makefile` is useful for development environments and will leverage OS specific packages to build `libgit2`. |
| 8 | +The `static.sh` will build all `libgit2` dependencies from source using `musl` toolchain. This enables for a full |
| 9 | +static binary with the freedom of configuring each of the dependencies in chain. |
5 | 10 |
|
6 | 11 | ### :warning: **Public usage discouraged**
|
7 | 12 |
|
@@ -42,86 +47,20 @@ while testing these against the git2go code before releasing the image.
|
42 | 47 | - [ ] [libgit2/git2go#836](https://github.com/libgit2/git2go/issues/836)
|
43 | 48 | - [ ] [libgit2/git2go#837](https://github.com/libgit2/git2go/issues/837)
|
44 | 49 |
|
45 |
| -## Usage |
46 |
| - |
47 |
| -To make use of the image published by the `Dockerfile`, copy over the `Makefile` from the image as a prerequisite to |
48 |
| -your Go build. Once copied over to the image, the set of targets can be used to compile `libgit2` for the |
49 |
| -`$BUILDPLATFORM` and/or `$TARGETPLATFORM` (see [example](#Dockerfile-example)). |
50 |
| - |
51 |
| -### Runtime dependencies |
52 |
| - |
53 |
| -The following dependencies should be present in the image running the application: |
54 |
| - |
55 |
| -- `libc6` |
56 |
| -- `ca-certificates` |
57 |
| -- `zlib1g/bookworm` |
58 |
| -- `libssl1.1/bookworm` |
59 |
| -- `libssh2-1/bookworm` |
60 |
| - |
61 |
| -**Note:** at present, all dependencies suffixed with `bookworm` must be installed from Debian's `bookworm` release, |
62 |
| -[due to a misconfiguration in `libssh2-1` in earlier versions][libssh2-1-misconfiguration]. |
63 |
| - |
64 |
| -### `Dockerfile` example |
65 |
| - |
66 |
| -```Dockerfile |
67 |
| -FROM --platform=$BUILDPLATFORM tonistiigi/xx:${XX_VERSION} AS xx |
68 |
| -FROM fluxcd/golang-with-libgit2 as libgit2 |
69 |
| - |
70 |
| -FROM --platform=$BUILDPLATFORM golang:1.17.6-bullseye as build |
71 |
| - |
72 |
| -# Copy the build utiltiies |
73 |
| -COPY --from=xx / / |
74 |
| -COPY --from=libgit2 /Makefile /libgit2/ |
75 |
| - |
76 |
| -# Install the libgit2 build dependencies |
77 |
| -RUN make -C /libgit2 cmake |
78 |
| - |
79 |
| -ARG TARGETPLATFORM |
80 |
| -RUN make -C /libgit2 dependencies |
81 |
| - |
82 |
| -# Compile and install libgit2 |
83 |
| -RUN FLAGS=$(xx-clang --print-cmake-defines) make -C /libgit2 libgit2 \ |
84 |
| - && mkdir -p /libgit2/lib/ \ |
85 |
| - && cp -d /usr/lib/$(xx-info triple)/libgit2.so* /libgit2/lib/ |
| 50 | +--- |
| 51 | +**NOTE** |
86 | 52 |
|
87 |
| -# Configure workspace |
88 |
| -WORKDIR /workspace |
| 53 | +The issues above do not affect libgit2 built with `static.sh` as all its |
| 54 | +dependencies have been configured to be optimal for its use, as the first supported version of libgit2 is `1.3.0`. |
89 | 55 |
|
90 |
| -# Copy modules manifests |
91 |
| -COPY go.mod go.mod |
92 |
| -COPY go.sum go.sum |
| 56 | +--- |
93 | 57 |
|
94 |
| -# Cache modules |
95 |
| -RUN go mod download |
96 |
| - |
97 |
| -# Copy source code |
98 |
| -COPY main.go main.go |
99 |
| - |
100 |
| -# Build the binary |
101 |
| -ENV CGO_ENABLED=1 |
102 |
| -ARG TARGETPLATFORM |
103 |
| -RUN xx-go build -o app \ |
104 |
| - main.go |
105 |
| - |
106 |
| -FROM debian:bookworm-slim as controller |
107 |
| - |
108 |
| -# Install runtime dependencies |
109 |
| -RUN apt update \ |
110 |
| - && apt install -y zlib1g/bookworm libssl1.1 libssh2-1 \ |
111 |
| - && apt install -y ca-certificates \ |
112 |
| - && apt clean \ |
113 |
| - && apt autoremove --purge -y \ |
114 |
| - && rm -rf /var/lib/apt/lists/* |
115 |
| - |
116 |
| -# Copy libgit2.so* |
117 |
| -COPY --from=build /libgit2/lib/ /usr/local/lib/ |
118 |
| -RUN ldconfig |
| 58 | +## Usage |
119 | 59 |
|
120 |
| -# Copy over binary from build |
121 |
| -COPY --from=build /workspace/app /usr/local/bin/ |
| 60 | +The [Dockerfile.test](./Dockerfile.test) file provides a working example on how to statically build a golang application that has a dependency to libgit2 and git2go. |
122 | 61 |
|
123 |
| -ENTRYPOINT [ "app" ] |
124 |
| -``` |
| 62 | +The example will statically build all dependencies based on the versions specified on `static.sh`. |
| 63 | +Then statically build the golang application and deploy it into an image based off `gcr.io/distroless/static`. |
125 | 64 |
|
126 | 65 | ## Contributing
|
127 | 66 |
|
@@ -162,6 +101,34 @@ In case changes happen to the `Dockerfile` while the `libgit2` version does not
|
162 | 101 | be suffixed with `-<seq num in range>`. For example, `libgit2-1.1.1-2` for the **third** container image
|
163 | 102 | with the same version.
|
164 | 103 |
|
| 104 | +### Debugging cross-compilation |
| 105 | + |
| 106 | +Below are a few tips on how to overcome cross-compilation issues: |
| 107 | + |
| 108 | +1) Ensure all qemu emulators are installed: |
| 109 | +```sh |
| 110 | +docker run -it --rm --privileged tonistiigi/binfmt --install all |
| 111 | +``` |
| 112 | + |
| 113 | +2) Check that the generated libraries are aligned with the target architecture: |
| 114 | + |
| 115 | +Leveraging `readelf` from `binutils` (i.e. `apk add binutils`), check the target machine |
| 116 | +architecture: |
| 117 | + |
| 118 | +```sh |
| 119 | +$ readelf -h /usr/local/aarch64-alpine-linux-musl/lib/libcrypto.a | grep Machine |sort -u |
| 120 | + Machine: AArch64 |
| 121 | +$ readelf -h /usr/local/aarch64-alpine-linux-musl/lib/libgit2.a | grep Machine | sort -u |
| 122 | + Machine: AArch64 |
| 123 | +$ readelf -h /usr/local/aarch64-alpine-linux-musl/lib/libssh2.a | grep Machine | sort -u |
| 124 | + Machine: AArch64 |
| 125 | +$ readelf -h /usr/local/aarch64-alpine-linux-musl/lib/libssl.a | grep Machine | sort -u |
| 126 | + Machine: AArch64 |
| 127 | +$ readelf -h /usr/local/aarch64-alpine-linux-musl/lib/libz.a | grep Machine | sort -u |
| 128 | + Machine: AArch64 |
| 129 | +``` |
| 130 | + |
| 131 | + |
165 | 132 | [xx]: https://github.com/tonistiigi/xx
|
166 | 133 | [Go container image]: https://hub.docker.com/_/golang
|
167 | 134 | [libgit2]: https://github.com/libgit2/libgit2
|
|
0 commit comments