102 lines
4.3 KiB
Docker
102 lines
4.3 KiB
Docker
# Multi-stage, multi-arch build for record-asr.
|
|
#
|
|
# docker build -t record-asr .
|
|
# docker buildx build --platform linux/amd64,linux/arm64 -t record-asr:latest --push .
|
|
#
|
|
# buildx builds each platform NATIVELY (the builder image matches the target
|
|
# arch), so cgo links the correct prebuilt .so for that arch and NO cross
|
|
# compiler is needed — unlike the bare `make build-arm64` path.
|
|
|
|
# ---- builder ----
|
|
FROM golang:1.22-bookworm AS builder
|
|
|
|
WORKDIR /src
|
|
# Allow overriding the Go module proxy, e.g. for restricted networks:
|
|
# docker build --build-arg GOPROXY=https://goproxy.cn,direct -t record-asr .
|
|
ARG GOPROXY=https://proxy.golang.org,direct
|
|
ENV GOPROXY=${GOPROXY}
|
|
# Cache module downloads (incl. the large sherpa-onnx-go .so) separately from
|
|
# source so code changes don't re-download deps.
|
|
COPY go.mod go.sum ./
|
|
RUN go mod download
|
|
|
|
COPY . .
|
|
|
|
# Build, then copy the prebuilt .so that match THIS builder's arch into /out/lib.
|
|
# The glob avoids hard-coding the sherpa-onnx-go-linux version.
|
|
RUN set -eux; \
|
|
CGO_ENABLED=1 go build -trimpath -o /out/record-asr .; \
|
|
arch="$(go env GOARCH)"; \
|
|
case "$arch" in \
|
|
amd64) libd=x86_64-unknown-linux-gnu;; \
|
|
arm64) libd=aarch64-unknown-linux-gnu;; \
|
|
*) echo "unsupported arch: $arch" >&2; exit 1;; \
|
|
esac; \
|
|
mkdir -p /out/lib; \
|
|
cp "$(go env GOMODCACHE)/github.com/k2-fsa/sherpa-onnx-go-linux@"*/lib/"$libd"/*.so /out/lib/
|
|
|
|
# ---- models: download SenseVoice int8 + silero VAD at BUILD time ----
|
|
# These are arch-independent ONNX files, so the same download serves every
|
|
# platform. Baking them into the image means the container starts instantly
|
|
# and needs no network at runtime. (One-time ~230MB cost per build.)
|
|
FROM debian:bookworm-slim AS models
|
|
RUN apt-get update \
|
|
&& apt-get install -y --no-install-recommends ca-certificates curl bzip2 \
|
|
&& rm -rf /var/lib/apt/lists/*
|
|
# Extract ONLY model.int8.onnx + tokens.txt from the release tarball (skip the
|
|
# test wavs / float model) to keep the layer lean. --strip-components=1 flattens
|
|
# the top archive dir so files land directly in /models/sensevoice/.
|
|
RUN mkdir -p /models/sensevoice \
|
|
&& curl -fsSL -o /tmp/sv.tar.bz2 \
|
|
"https://github.com/k2-fsa/sherpa-onnx/releases/download/asr-models/sherpa-onnx-sense-voice-zh-en-ja-ko-yue-int8-2024-07-17.tar.bz2" \
|
|
&& tar -xjf /tmp/sv.tar.bz2 -C /models/sensevoice \
|
|
--strip-components=1 --wildcards --no-anchored 'model.int8.onnx' 'tokens.txt' \
|
|
&& rm -f /tmp/sv.tar.bz2 \
|
|
&& curl -fsSL -o /models/silero_vad.onnx \
|
|
"https://github.com/k2-fsa/sherpa-onnx/releases/download/asr-models/silero_vad.onnx" \
|
|
&& test -s /models/sensevoice/model.int8.onnx \
|
|
&& test -s /models/sensevoice/tokens.txt \
|
|
&& test -s /models/silero_vad.onnx \
|
|
&& ls -lh /models/sensevoice /models/silero_vad.onnx
|
|
|
|
# ---- runtime (glibc; sherpa-onnx .so are glibc-built, so NOT alpine/musl) ----
|
|
FROM debian:bookworm-slim
|
|
|
|
# APT_MIRROR: optionally swap deb.debian.org for a faster regional mirror, e.g.
|
|
# docker build --build-arg APT_MIRROR=mirrors.tuna.tsinghua.edu.cn -t record-asr .
|
|
# Defaults to the upstream deb.debian.org (no swap). ffmpeg (~250MB of codec
|
|
# libs) decodes m4a/aac/opus/wma — beep is pure-Go for wav/mp3/flac/ogg only.
|
|
ARG APT_MIRROR=
|
|
RUN set -eux; \
|
|
if [ -n "$APT_MIRROR" ]; then \
|
|
f=/etc/apt/sources.list.d/debian.sources; \
|
|
if [ -f "$f" ]; then sed -i "s|deb.debian.org|$APT_MIRROR|g; s|security.debian.org|$APT_MIRROR|g" "$f"; \
|
|
else sed -i "s|deb.debian.org|$APT_MIRROR|g; s|security.debian.org|$APT_MIRROR|g" /etc/apt/sources.list; fi; \
|
|
fi; \
|
|
apt-get update \
|
|
&& apt-get install -y --no-install-recommends ca-certificates curl ffmpeg \
|
|
&& rm -rf /var/lib/apt/lists/*
|
|
|
|
WORKDIR /app
|
|
COPY --from=builder /out/record-asr /app/record-asr
|
|
COPY --from=builder /out/lib /app/lib
|
|
COPY --from=models /models /models
|
|
|
|
# Defaults; override via -e / compose. Models are baked in at /models, so
|
|
# startup skips the download entirely. Only /app/data (tasks + uploads) is a
|
|
# volume; it never holds models.
|
|
ENV ASR_ADDR=:8080 \
|
|
ASR_DATA_DIR=/app/data \
|
|
ASR_MODEL_DIR=/models \
|
|
ASR_DOWNLOAD_TIMEOUT=1800 \
|
|
LD_LIBRARY_PATH=/app/lib
|
|
|
|
VOLUME /app/data
|
|
EXPOSE 8080
|
|
|
|
HEALTHCHECK --interval=30s --timeout=5s --start-period=30s --retries=3 \
|
|
CMD curl -fsS http://127.0.0.1:8080/healthz || exit 1
|
|
|
|
ENTRYPOINT ["/app/record-asr"]
|
|
|