Compare commits

..
Author SHA1 Message Date
Joachim Schlöffel b6a87a3f2e upgrade seaweedfs to 4.41 and patch gitea's new checksum
Build Alpine Packages / build-and-publish (v3.24, 3.24) (pull_request) Successful in 30m26s
2026-08-13 12:31:27 +02:00
Joachim Schlöffel e6d9b173f2 Merge branch 'main' of ssh://code.factoring.digital:2022/public/alpine-packages
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Failing after 51s
2026-07-28 12:05:13 +02:00
Joachim Schlöffel 107e17b959 Gitea patch upgrade to 1.27.1 2026-07-28 12:04:49 +02:00
fspjoandJoachim Schlöffel 57bf04fa87 PKG Upgrade 2026-07-24 (#4)
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 2h27m37s
---------

Co-authored-by: Joachim Schlöffel <me@joachim-schloeffel.com>
Reviewed-on: #4
2026-07-24 16:54:31 +02:00
Joachim Schlöffel 88abf51ca5 Gitea version bump to 1.27.0
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 2h20m16s
2026-07-16 11:01:59 +02:00
Joachim Schlöffel 85122866ac fix publisher bug for multiarch packages
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 18s
2026-07-13 03:06:06 +02:00
Joachim Schlöffel 89db986774 Optimize Alpine packaging workflow
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 2h16m43s
2026-07-12 10:24:15 +02:00
Joachim Schlöffel faf7d5e404 Filter stale APKs from CI package cache
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Has been cancelled
2026-07-12 10:09:45 +02:00
Joachim Schlöffel 7781653941 Use repository owner as CI packager
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 27m36s
2026-07-12 08:05:55 +02:00
Joachim Schlöffel b19a3288fd Update SeaweedFS and add outdated checks
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Has been cancelled
2026-07-12 07:49:15 +02:00
Joachim Schlöffel 95834e55d5 simplify CI runtime checks
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 26m54s
2026-07-09 13:58:55 +02:00
Joachim Schlöffel 95f8f1597a fix package key check during CI build
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Failing after 27m11s
2026-07-09 10:54:06 +02:00
Joachim Schlöffel 2be2a6d5b0 fix lavinMQ runtime test
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Failing after 38s
2026-07-09 10:47:42 +02:00
Joachim Schlöffel a812b075d0 docs update
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Failing after 29m40s
2026-07-09 10:08:25 +02:00
Joachim Schlöffel 6b8488d7cc Skip cached Alpine package rebuilds in CI
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Has been cancelled
2026-07-09 09:59:35 +02:00
Joachim Schlöffel 368a112568 Merge branch 'main' of ssh://code.factoring.digital:2022/public/alpine-packages
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Has been cancelled
2026-07-09 09:35:47 +02:00
Joachim Schlöffel 04b1244a8c Fix LavinMQ OpenRC data ownership 2026-07-09 09:34:16 +02:00
fspjo de967b8d36 Merge pull request 'Add Gitea 1.26.4' (#3) from add-gitea-1.26.4 into main
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 29m44s
2026-07-08 18:19:27 +02:00
Joachim Schlöffel a3c4d09e65 Add Gitea 1.26.4 Alpine package
Build Alpine Packages / build-and-publish (v3.24, 3.24) (pull_request) Successful in 29m45s
2026-07-08 18:18:04 +02:00
fspjo dfd92c522b Merge pull request 'Add LavinMQ Alpine Package' (#2) from add-lavinmq-alpine-package into main
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 29m14s
2026-07-08 15:26:22 +02:00
Joachim Schlöffel 2c3107feb4 Add LavinMQ Alpine package
Build Alpine Packages / build-and-publish (v3.24, 3.24) (pull_request) Successful in 29m11s
2026-07-08 14:54:16 +02:00
fspjo 08e516475f Merge pull request 'Update GreptimeDB to 1.1.2' (#1) from update-greptimedb-1.1.2 into main
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 27m16s
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 27m13s
2026-07-06 14:54:07 +02:00
Joachim Schlöffel 9462c9a304 greptimedb version bump to 1.1.2
Build Alpine Packages / build-and-publish (v3.23, 3.23) (pull_request) Successful in 25m18s
Build Alpine Packages / build-and-publish (v3.24, 3.24) (pull_request) Successful in 25m24s
2026-07-06 10:19:56 +02:00
Joachim Schlöffel 47c398a6ae Add Alpine package runtime tests
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 25m39s
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 26m14s
2026-07-06 09:37:18 +02:00
Joachim Schlöffel e076b3249a tighten docs 2026-07-05 23:21:24 +02:00
Joachim Schlöffel 1c4b598b5c Add Alpine v3.24 package target
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 26m38s
Build Alpine Packages / build-and-publish (v3.24, 3.24) (push) Successful in 38m1s
2026-07-05 23:18:35 +02:00
Joachim Schlöffel 4efe12f250 shorter docs
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 25m36s
2026-06-09 21:48:32 +02:00
Joachim Schlöffel b329cd0ccc Document preserving Gitea Alpine key filename
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 25m2s
2026-06-09 14:25:09 +02:00
Joachim Schlöffel ca64a3e993 Skip duplicate APK filenames when publishing 2026-06-09 13:43:50 +02:00
Joachim Schlöffel 3049d872e0 Add GreptimeDB dashboard assets source
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 24m50s
2026-06-09 13:33:10 +02:00
Joachim Schlöffel bef07e3e22 Add GreptimeDB docs package and trim CI matrix
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Failing after 3m44s
2026-06-09 13:23:51 +02:00
Joachim Schlöffel 05188cc390 Add SeaweedFS package README links
Build Alpine Packages / build-and-publish (edge, edge) (push) Successful in 35m36s
Build Alpine Packages / build-and-publish (v3.23, 3.23) (push) Successful in 35m33s
2026-06-09 11:04:52 +02:00
Joachim Schlöffel 74207600cc Build Alpine packages for stable and edge 2026-06-09 11:00:42 +02:00
Joachim Schlöffel 2a965b05d5 Update README package repository URL
Build Alpine Packages / build-and-publish (push) Successful in 30m46s
2026-06-09 10:51:04 +02:00
Joachim Schlöffel 50e8eaa62a Cache Rust build artifacts for Alpine packages
Build Alpine Packages / build-and-publish (push) Has been cancelled
2026-06-09 10:47:17 +02:00
Joachim Schlöffel 11ef6456af Add GreptimeDB Alpine service packaging
Build Alpine Packages / build-and-publish (push) Successful in 35m5s
2026-06-09 09:54:39 +02:00
Joachim Schlöffel f3ff86263a fix CI build (optimize memory usage during build)
Build Alpine Packages / build-and-publish (push) Successful in 39m16s
2026-06-09 01:21:29 +02:00
Joachim Schlöffel 43407a1f3f fix CI build (rustup init)
Build Alpine Packages / build-and-publish (push) Failing after 20m9s
2026-06-09 00:53:56 +02:00
Joachim Schlöffel 1d112d23d1 fix CI build (rustup)
Build Alpine Packages / build-and-publish (push) Failing after 27s
2026-06-09 00:05:23 +02:00
Joachim Schlöffel 67fcee9099 fix CI build
Build Alpine Packages / build-and-publish (push) Failing after 5m2s
2026-06-08 23:51:02 +02:00
66 changed files with 2413 additions and 390 deletions
+5
View File
@@ -0,0 +1,5 @@
.git
.cache
packages
packaging/**/pkg
packaging/**/src
+64 -7
View File
@@ -1,6 +1,8 @@
name: Build Alpine Packages name: Build Alpine Packages
on: on:
schedule:
- cron: "17 5 * * 1"
push: push:
branches: branches:
- master - master
@@ -13,36 +15,91 @@ on:
jobs: jobs:
build-and-publish: build-and-publish:
runs-on: ubuntu-latest runs-on: ubuntu-latest
strategy:
matrix:
include:
- alpine_version: "3.24"
alpine_registry_branch: "v3.24"
container: container:
image: alpine:3.23 image: "alpine:${{ matrix.alpine_version }}"
env: env:
ALPINE_VERSION: "3.23" ALPINE_VERSION: "${{ matrix.alpine_version }}"
ALPINE_ARCHES: "x86_64 aarch64" ALPINE_ARCHES: "x86_64 aarch64"
ALPINE_REGISTRY_BRANCH: "v3.23" ALPINE_REGISTRY_BRANCH: "${{ matrix.alpine_registry_branch }}"
ALPINE_REGISTRY_REPOSITORY: "${{ vars.PACKAGE_NAME }}" ALPINE_REGISTRY_REPOSITORY: "${{ vars.PACKAGE_NAME }}"
INSTANCE_URL: "${{ vars.INSTANCE_URL }}" INSTANCE_URL: "${{ vars.INSTANCE_URL }}"
PACKAGE_OWNER: "${{ vars.PACKAGE_OWNER }}" PACKAGE_OWNER: "${{ vars.PACKAGE_OWNER }}"
PACKAGE_USER: "${{ secrets.PACKAGE_USER }}" PACKAGE_USER: "${{ secrets.PACKAGE_USER }}"
PACKAGE_TOKEN: "${{ secrets.PACKAGE_TOKEN }}" PACKAGE_TOKEN: "${{ secrets.PACKAGE_TOKEN }}"
PACKAGER: "Joachim Schlöffel <me@joachim-schloeffel.com>" PACKAGER: "${{ gitea.repository_owner }}"
ALPINE_APK_REPO_CACHE: "/cache/public-alpine-packages/${{ matrix.alpine_registry_branch }}/apk-repo"
CARGO_HOME: "/cache/public-alpine-packages/${{ matrix.alpine_registry_branch }}/greptimedb/cargo"
RUSTUP_HOME: "/cache/public-alpine-packages/${{ matrix.alpine_registry_branch }}/greptimedb/rustup"
CARGO_TARGET_DIR: "/cache/public-alpine-packages/${{ matrix.alpine_registry_branch }}/greptimedb/target"
steps: steps:
- name: Prepare Environment - name: Prepare Environment
run: | run: |
apk add --no-cache --update abuild-rootbld alpine-sdk atools-apkbuild-lint bash ca-certificates curl doas git nodejs sudo tar apk add --no-cache --update abuild-rootbld alpine-sdk atools-apkbuild-lint bash ca-certificates curl doas git nodejs rsync shellcheck sudo tar
mkdir -p "$ALPINE_APK_REPO_CACHE" "$CARGO_HOME" "$RUSTUP_HOME" "$CARGO_TARGET_DIR"
chown -R 1000:1000 /cache/public-alpine-packages/${{ matrix.alpine_registry_branch }}
- name: Checkout - name: Checkout
uses: actions/checkout@v3 uses: actions/checkout@v3
- name: Build packages - name: Select packages
run: | run: |
scripts/apk/clean.sh scripts/apk/clean.sh
find packaging/alpine/local -mindepth 2 -maxdepth 2 -name APKBUILD -exec apkbuild-lint {} + find packaging/alpine/local -mindepth 2 -maxdepth 2 -name APKBUILD -exec apkbuild-lint {} +
scripts/apk/lint-shell.sh
scripts/apk/outdated.sh | tee update-check.txt
if [ -n "${GITHUB_STEP_SUMMARY:-}" ]; then
{
echo "## Upstream update check"
echo
echo '```text'
cat update-check.txt
echo '```'
} >> "$GITHUB_STEP_SUMMARY"
fi
- name: Prepare package cache
if: github.event_name != 'schedule'
run: |
scripts/apk/ci-package-cache.sh prepare
- name: Build packages
if: github.event_name != 'schedule'
run: |
scripts/apk/ci-build.sh scripts/apk/ci-build.sh
scripts/apk/ci-package-cache.sh sync
scripts/apk/export-ci-assets.sh
scripts/apk/list-packages.sh scripts/apk/list-packages.sh
- name: Check artifact upload support
if: github.event_name != 'schedule'
id: artifact-upload
run: |
if [ -n "${ACTIONS_RUNTIME_TOKEN:-}" ]; then
echo "available=true" >> "$GITHUB_OUTPUT"
else
echo "available=false" >> "$GITHUB_OUTPUT"
fi
- name: Upload generated CI assets
if: github.event_name != 'schedule' && steps.artifact-upload.outputs.available == 'true'
uses: actions/upload-artifact@v3
with:
name: greptimedb-musl-binaries-${{ matrix.alpine_registry_branch }}
path: packages/ci-assets/
- name: Smoke test - name: Smoke test
if: github.event_name != 'schedule'
run: scripts/apk/ci-smoke.sh run: scripts/apk/ci-smoke.sh
- name: Runtime test
if: github.event_name != 'schedule'
run: scripts/apk/runtime-test.sh
- name: Publish Alpine packages - name: Publish Alpine packages
if: github.event_name != 'pull_request' if: github.event_name != 'pull_request' && github.event_name != 'schedule'
run: scripts/apk/publish-gitea.sh run: scripts/apk/publish-gitea.sh
+124 -223
View File
@@ -1,171 +1,57 @@
# Alpine Packages # Alpine Packages
Alpine 3.23 packaging for internal packages. Alpine stable packaging for internal packages. This repository carries selected
upstream releases ahead of Alpine community packages when we need newer
features, packaging fixes, or service layouts on the current Alpine branch.
This repository builds signed `x86_64` and `aarch64` APKs and publishes them to Packages are either source builds or binary repackages:
the Gitea Alpine package registry under:
- Source builds compile upstream source releases inside the Alpine build
environment and link against Alpine libraries.
- Binary repackages wrap official upstream Linux release artifacts in Alpine
package metadata, OpenRC services, config defaults, and role subpackages.
```text ```text
https://code.factoring.digital/api/packages/fsp-ops/alpine/v3.23/seaweedfs-alpine https://code.factoring.digital/api/packages/public/alpine/v3.24/alpine-packages
``` ```
## Available Packages
| Package | APK Name | Package Version | Package Type | Purpose |
|-----------------------------------------------------------|--------------|-----------------|----------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------|
| [SeaweedFS](packaging/alpine/local/seaweedfs/README.md) | `seaweedfs` | `4.40` | Binary repackaging of official upstream release tarballs | Ships current SeaweedFS features with Alpine OpenRC role splits. |
| [GreptimeDB](packaging/alpine/local/greptimedb/README.md) | `greptimedb` | `1.1.4` | Source build from upstream release | Provides a current GreptimeDB build and component OpenRC packages before it is available from Alpine community. |
| [LavinMQ](packaging/alpine/local/lavinmq/README.md) | `lavinmq` | `2.9.1` | Source build from upstream release | Provides a current LavinMQ build on Alpine 3.24 with matching Crystal support. |
| [Gitea](packaging/alpine/local/gitea/README.md) | `gitea` | `1.27.0` | Binary repackaging of official upstream release binaries | Ships current Gitea releases with the expected Alpine runtime layout and OpenRC service. |
## Use In Production ## Use In Production
### Add The Package Repository ### Add The Package Repository
Install the registry signing key on each Alpine node: Install the registry key:
```sh ```sh
curl -fsSLo /etc/apk/keys/fsp-ops-alpine.rsa.pub \ cd /etc/apk/keys
https://code.factoring.digital/api/packages/fsp-ops/alpine/key curl -fsSLOJ https://code.factoring.digital/api/packages/public/alpine/key
``` ```
Add the package repository: Add the repository for the node's Alpine branch:
```sh ```sh
printf '%s\n' \ printf '%s\n' \
'https://code.factoring.digital/api/packages/fsp-ops/alpine/v3.23/seaweedfs-alpine' \ 'https://code.factoring.digital/api/packages/public/alpine/v3.24/alpine-packages' \
>> /etc/apk/repositories >> /etc/apk/repositories
apk update apk update
``` ```
If the registry is private, include a Gitea user and package token in the Private registry URL format:
repository URL:
```text ```text
https://<user>:<token>@code.factoring.digital/api/packages/fsp-ops/alpine/v3.23/seaweedfs-alpine https://<user>:<token>@code.factoring.digital/api/packages/public/alpine/v3.24/alpine-packages
``` ```
### Install SeaweedFS Node Roles ## Contribution
Install the base package plus only the OpenRC role packages needed on that node.
For a single-node test or a compact small deployment:
```sh
apk add seaweedfs \
seaweedfs-master-openrc \
seaweedfs-volume-openrc \
seaweedfs-filer-openrc
```
For separated production nodes, install only the role running there:
```sh
apk add seaweedfs seaweedfs-master-openrc
apk add seaweedfs seaweedfs-volume-openrc
apk add seaweedfs seaweedfs-filer-openrc
```
Available OpenRC role packages:
```text
seaweedfs-master-openrc -> /etc/init.d/seaweedfs.master
seaweedfs-volume-openrc -> /etc/init.d/seaweedfs.volume
seaweedfs-filer-openrc -> /etc/init.d/seaweedfs.filer
seaweedfs-s3-openrc -> /etc/init.d/seaweedfs.s3
seaweedfs-webdav-openrc -> /etc/init.d/seaweedfs.webdav
seaweedfs-sftp-openrc -> /etc/init.d/seaweedfs.sftp
seaweedfs-admin-openrc -> /etc/init.d/seaweedfs.admin
seaweedfs-worker-openrc -> /etc/init.d/seaweedfs.worker
```
The package name is `seaweedfs`, matching Alpine aports. If a node already has
Alpine's old generic OpenRC package installed, remove it before installing a
role-specific split:
```sh
apk del seaweedfs-openrc
apk add seaweedfs seaweedfs-master-openrc
```
### Configure Services
Runtime files are installed in the usual Alpine locations:
```text
/usr/bin/weed
/etc/seaweedfs/*.toml
/etc/conf.d/seaweedfs.*
/etc/init.d/seaweedfs.*
```
Edit `/etc/conf.d/seaweedfs.<role>` for command-line flags and
`/etc/seaweedfs/*.toml` for SeaweedFS config. The packaged defaults are short
and production-neutral; full upstream example configs are in:
```text
/usr/share/doc/seaweedfs/examples/
```
Enable and start only the services needed on the node:
```sh
rc-update add seaweedfs.master default
rc-service seaweedfs.master start
rc-update add seaweedfs.volume default
rc-service seaweedfs.volume start
rc-update add seaweedfs.filer default
rc-service seaweedfs.filer start
```
Check the installed binary and service state:
```sh
weed version
rc-service seaweedfs.master status
```
### Optional Packages
Install docs and generated examples:
```sh
apk add seaweedfs-doc
```
Install bash completion:
```sh
apk add bash-completion seaweedfs-bash-completion
```
`seaweedfs-bash-completion` is also selected automatically when `seaweedfs` and
`bash-completion` are installed together.
### Upgrade Or Pin
Use normal Alpine package operations:
```sh
apk upgrade seaweedfs
rc-service seaweedfs.master restart
```
Pin a specific package build when needed:
```sh
apk add seaweedfs=4.31-r3
```
### Install GreptimeDB
Install GreptimeDB:
```sh
apk add greptimedb
```
Check the installed binary:
```sh
greptime --version
```
## Background And Contribution
### Package Layout ### Package Layout
@@ -175,24 +61,6 @@ Package sources live under:
packaging/alpine/local/<pkgname>/ packaging/alpine/local/<pkgname>/
``` ```
Currently packaged:
```text
seaweedfs SeaweedFS 4.31 release binary and OpenRC role splits
greptimedb GreptimeDB 1.0.2 built from source for x86_64
```
### SeaweedFS Package
The APKBUILD repackages the official SeaweedFS Linux release tarballs. It does
not build SeaweedFS from source. The package installs:
- `weed` as `/usr/bin/weed`
- minimal active config under `/etc/seaweedfs/`
- role-specific OpenRC subpackages
- upstream example configs under `/usr/share/doc/seaweedfs/examples/`
- generated bash completion as a separate subpackage
Local build output is written under: Local build output is written under:
```text ```text
@@ -209,28 +77,39 @@ Signing keys and distfiles are cached under:
### Build Commands ### Build Commands
```sh ```sh
mise run apk:lint $ mise tasks
mise run apk:build Name Description
mise run apk:build-all apk:build Build the Alpine package in Docker for the default architecture
mise run apk:packages apk:build-aarch64 Build the Alpine package in Docker for aarch64
mise run apk:smoke apk:build-all Build the Alpine package in Docker for all configured architectures
mise run apk:test-install apk:build-x86_64 Build the Alpine package in Docker for x86_64
mise run apk:test-shell apk:checksum Refresh APKBUILD checksums in Docker
mise run apk:publish-check apk:ci-build Build all configured Alpine packages directly in the current Alpine...
apk:ci-smoke Install-test built packages directly in the current Alpine environment
apk:clean Remove generated Alpine package build outputs
apk:lint Run Alpine APKBUILD lint in Docker
apk:lint-shell Run ShellCheck for packaging automation
apk:packages List built Alpine packages and dependencies
apk:publish-check Run lint, multi-arch build, package listing, and smoke test
apk:publish-gitea Publish built packages to the Gitea Alpine package registry
apk:outdated Check packaged upstream versions against latest GitHub releases
apk:shell Open an Alpine package build shell in Docker
apk:smoke Install-test built packages from the local repository in Docker
apk:test-install Test README installation instructions in a fresh Alpine container
apk:test-shell Open an Alpine shell with the local APK repository configured
apk:update-generated Refresh packaged upstream examples and shell completions
apk:runtime-test Run package-local Docker runtime tests against the local...
gitea-workflow-build Run the Gitea build workflow locally through act as a pull_request event
``` ```
`apk:build` targets `x86_64` by default. Multi-arch builds target `x86_64` and `apk:build` targets `x86_64` by default. Multi-arch builds target `x86_64` and
`aarch64`; override with `ALPINE_ARCHES` when needed: `aarch64`:
```sh ```sh
ALPINE_ARCHES="x86_64 aarch64" mise run apk:build-all ALPINE_ARCHES="x86_64 aarch64" mise run apk:build-all
``` ```
Unqualified build and install-test tasks discover all packages. GreptimeDB is a Limit package selection with `ALPINE_PACKAGE` or `ALPINE_PACKAGES`:
source build and can take close to an hour; it is limited to `x86_64` during
production evaluation. Target fast package work explicitly:
Build or test a subset of packages with `ALPINE_PACKAGE` or `ALPINE_PACKAGES`:
```sh ```sh
ALPINE_PACKAGE=seaweedfs mise run apk:build ALPINE_PACKAGE=seaweedfs mise run apk:build
@@ -239,71 +118,96 @@ ALPINE_PACKAGE=seaweedfs mise run apk:test-install
ALPINE_PACKAGE=greptimedb mise run apk:checksum ALPINE_PACKAGE=greptimedb mise run apk:checksum
ALPINE_PACKAGE=greptimedb mise run apk:build ALPINE_PACKAGE=greptimedb mise run apk:build
ALPINE_PACKAGE=greptimedb SKIP_BUILD=1 mise run apk:test-install ALPINE_PACKAGE=greptimedb SKIP_BUILD=1 mise run apk:test-install
ALPINE_PACKAGE=lavinmq mise run apk:build
ALPINE_PACKAGE=lavinmq SKIP_BUILD=1 mise run apk:test-install
ALPINE_PACKAGE=gitea mise run apk:build
ALPINE_PACKAGE=gitea SKIP_BUILD=1 mise run apk:test-install
``` ```
Use the test shell to inspect the package in Alpine with the current build Override Docker cache scope:
installed:
```sh
ALPINE_APK_CACHE_SCOPE=public-alpine-packages ALPINE_PACKAGE=greptimedb mise run apk:build
ALPINE_APK_CACHE_PREFIX=alpine-apk-ci ALPINE_PACKAGE=greptimedb mise run apk:build
```
Local packages use `local` as the default package metadata identity. Override it
when needed:
```sh
PACKAGER="Example Builder <builder@example.com>" ALPINE_PACKAGE=seaweedfs mise run apk:build
```
Open an Alpine package build shell:
```sh ```sh
ALPINE_PACKAGE=seaweedfs mise run apk:shell ALPINE_PACKAGE=seaweedfs mise run apk:shell
mise run apk:test-shell
``` ```
Use the install test to validate the production instructions against the local Run the install test:
package repository in a fresh Alpine container:
```sh ```sh
mise run apk:test-install mise run apk:test-install
``` ```
Use `SKIP_BUILD=1` to reuse existing local packages: Reuse existing local packages:
```sh ```sh
SKIP_BUILD=1 mise run apk:test-install SKIP_BUILD=1 mise run apk:test-install
SKIP_BUILD=1 mise run apk:test-shell SKIP_BUILD=1 mise run apk:test-shell
``` ```
`apk:test-shell` opens an Alpine shell with the local APK repository configured.
Install whichever built packages you want inside the container:
```sh
apk add seaweedfs seaweedfs-master-openrc
weed version
apk add greptimedb greptimedb-docs greptimedb-standalone-openrc
greptime --version
```
Run package-local runtime tests:
```sh
mise run apk:runtime-test
ALPINE_PACKAGE=seaweedfs mise run apk:runtime-test
ALPINE_VERSION=3.24 mise run apk:runtime-test
```
### Adding Packages ### Adding Packages
Each package lives under: Package path:
```text ```text
packaging/alpine/local/<pkgname>/ packaging/alpine/local/<pkgname>/
``` ```
The only required file is `APKBUILD`. Package-specific helpers can be added as Optional package hooks:
hooks:
```text ```text
packaging/alpine/local/<pkgname>/scripts/test-install.sh packaging/alpine/local/<pkgname>/scripts/test-install.sh
packaging/alpine/local/<pkgname>/scripts/update-generated-sources.sh packaging/alpine/local/<pkgname>/scripts/update-generated-sources.sh
packaging/alpine/local/<pkgname>/scripts/runtime-test.sh
``` ```
Repo-level tasks discover all `packaging/alpine/local/*/APKBUILD` files. Hook Start from the blueprint:
tasks skip packages that do not provide the requested hook.
Start new packages from the blueprint:
```text ```text
packaging/alpine/blueprint/ packaging/alpine/blueprint/
``` ```
For compiled software, declare build tools in `makedepends` and use normal
Alpine `build()`, `check()`, and `package()` functions in the package's
`APKBUILD`.
### Generated Package Sources ### Generated Package Sources
Generated files should live next to the package's `APKBUILD` so Generated package sources live next to the package `APKBUILD`:
`abuild checksum` can track them as ordinary package sources. For SeaweedFS,
that includes:
```text ```text
packaging/alpine/local/seaweedfs/example-*.toml packaging/alpine/local/seaweedfs/example-*.toml
packaging/alpine/local/seaweedfs/weed.bash-completion packaging/alpine/local/seaweedfs/weed.bash-completion
``` ```
Refresh generated sources through package-local hooks: Refresh generated sources:
```sh ```sh
mise run apk:update-generated mise run apk:update-generated
@@ -311,20 +215,33 @@ ALPINE_PACKAGE=seaweedfs mise run apk:update-generated
mise run apk:checksum mise run apk:checksum
``` ```
Run `apk:checksum` after changing any file listed in `source=`. ### Upstream Update Visibility
Check whether packaged upstream versions are current:
```sh
mise run apk:outdated
ALPINE_PACKAGE=seaweedfs mise run apk:outdated
```
By default this is a warning-only signal. To make outdated or unknown package
versions fail the command:
```sh
APK_UPDATE_CHECK_MODE=fail mise run apk:outdated
```
### Gitea Workflow ### Gitea Workflow
The workflow at `.gitea/workflows/build.yml` builds in an `alpine:3.23` `.gitea/workflows/build.yml` builds and publishes `v3.24`. Pull requests
container and publishes on push or tag. It skips publishing for pull request build only.
events.
Repository variables: Repository variables:
```text ```text
INSTANCE_URL=https://code.factoring.digital INSTANCE_URL=https://code.factoring.digital
PACKAGE_OWNER=fsp-ops PACKAGE_OWNER=public
PACKAGE_NAME=seaweedfs-alpine PACKAGE_NAME=alpine-packages
``` ```
Repository secrets: Repository secrets:
@@ -334,42 +251,24 @@ PACKAGE_USER=<gitea package publisher>
PACKAGE_TOKEN=<token with package write access> PACKAGE_TOKEN=<token with package write access>
``` ```
Pre-check the workflow locally with `act`: Check the workflow locally:
```sh ```sh
mise run gitea-workflow-build mise run gitea-workflow-build
``` ```
Publish already-built local packages manually: Publish local packages:
```sh ```sh
INSTANCE_URL=https://code.factoring.digital \ INSTANCE_URL=https://code.factoring.digital \
PACKAGE_OWNER=fsp-ops \ PACKAGE_OWNER=public \
PACKAGE_NAME=seaweedfs-alpine \ PACKAGE_NAME=alpine-packages \
PACKAGE_USER=... \ PACKAGE_USER=... \
PACKAGE_TOKEN=... \ PACKAGE_TOKEN=... \
mise run apk:publish-gitea mise run apk:publish-gitea
``` ```
### Alpine Package Rules ### Checklist
Do:
- Keep local package sources next to the `APKBUILD`.
- Put full upstream scaffolds in `/usr/share/doc/seaweedfs/examples/`, not active `/etc`.
- Install only the OpenRC role packages needed on each node.
- Keep `/etc/conf.d` defaults short and production-neutral.
- Increment `pkgrel` for package-only changes; reset it when `pkgver` changes.
- Run `mise run apk:publish-check` before opening a PR.
Don't:
- Edit generated `src/`, `pkg/`, or `packages/` output.
- Hand-edit checksum lines when `abuild checksum` can update them.
- Install all OpenRC roles by default.
- Put long upstream examples into active `/etc` defaults.
### Practical PR Checklist
Before opening a PR, run: Before opening a PR, run:
@@ -377,12 +276,14 @@ Before opening a PR, run:
mise run apk:publish-check mise run apk:publish-check
mise run gitea-workflow-build mise run gitea-workflow-build
mise run apk:test-install mise run apk:test-install
mise run apk:runtime-test
``` ```
Then test at least one installed role in the package shell: Then test at least one installed role in the package shell:
```sh ```sh
mise run apk:test-shell mise run apk:test-shell
apk add seaweedfs seaweedfs-master-openrc
rc-service seaweedfs.master start rc-service seaweedfs.master start
weed version weed version
``` ```
-15
View File
@@ -1,15 +0,0 @@
#!/usr/bin/env -S mise tool-stub
# SeaweedFS 4.31 release binary.
version = "4.31"
bin = "weed"
[platforms.linux-x64]
url = "https://github.com/seaweedfs/seaweedfs/releases/download/4.31/linux_amd64.tar.gz"
checksum = "sha256:81103c53453fddfa75d9d611cd3e61aa57e7a3099dc7a1de5977ab4b19211958"
size = 43223476
[platforms.linux-arm64]
url = "https://github.com/seaweedfs/seaweedfs/releases/download/4.31/linux_arm64.tar.gz"
checksum = "sha256:76ac1ffce87a2a710a3913282a19de6d9a3785f4a3586556858ec7b81a87d958"
size = 38036794
+14 -2
View File
@@ -1,6 +1,5 @@
[tools] [tools]
act = "latest" act = "latest"
codex = "latest"
docker-cli = "latest" docker-cli = "latest"
shellcheck = "latest" shellcheck = "latest"
@@ -36,6 +35,10 @@ run = "scripts/apk/update-generated-sources.sh"
description = "Run Alpine APKBUILD lint in Docker" description = "Run Alpine APKBUILD lint in Docker"
run = "scripts/apk/build.sh lint" run = "scripts/apk/build.sh lint"
[tasks."apk:lint-shell"]
description = "Run ShellCheck for packaging automation"
run = "scripts/apk/lint-shell.sh"
[tasks."apk:smoke"] [tasks."apk:smoke"]
description = "Install-test built packages from the local repository in Docker" description = "Install-test built packages from the local repository in Docker"
run = "scripts/apk/smoke.sh" run = "scripts/apk/smoke.sh"
@@ -45,17 +48,26 @@ description = "Install-test built packages directly in the current Alpine enviro
run = "scripts/apk/ci-smoke.sh" run = "scripts/apk/ci-smoke.sh"
[tasks."apk:test-shell"] [tasks."apk:test-shell"]
description = "Open an Alpine shell with the current local package build installed" description = "Open an Alpine shell with the local APK repository configured"
run = "scripts/apk/test-shell.sh" run = "scripts/apk/test-shell.sh"
[tasks."apk:test-install"] [tasks."apk:test-install"]
description = "Test README installation instructions in a fresh Alpine container" description = "Test README installation instructions in a fresh Alpine container"
run = "scripts/apk/test-install.sh" run = "scripts/apk/test-install.sh"
[tasks."apk:runtime-test"]
description = "Run package-local Docker runtime tests against the local Alpine repository"
run = "scripts/apk/runtime-test.sh"
env = { ALPINE_ARCH = "x86_64", ALPINE_REPO_NAME = "local", ALPINE_VERSION = "3.24" }
[tasks."apk:packages"] [tasks."apk:packages"]
description = "List built Alpine packages and dependencies" description = "List built Alpine packages and dependencies"
run = "scripts/apk/list-packages.sh" run = "scripts/apk/list-packages.sh"
[tasks."apk:outdated"]
description = "Check packaged upstream versions against latest GitHub releases"
run = "scripts/apk/outdated.sh"
[tasks."apk:publish-check"] [tasks."apk:publish-check"]
description = "Run lint, multi-arch build, package listing, and smoke test" description = "Run lint, multi-arch build, package listing, and smoke test"
run = "scripts/apk/publish-check.sh" run = "scripts/apk/publish-check.sh"
+3
View File
@@ -12,6 +12,8 @@ Optional package-local hooks:
- `scripts/test-install.sh` validates README-style installation instructions. - `scripts/test-install.sh` validates README-style installation instructions.
- `scripts/update-generated-sources.sh` refreshes generated files that are - `scripts/update-generated-sources.sh` refreshes generated files that are
listed in `source=`. listed in `source=`.
- `scripts/runtime-test.sh` validates an installed package in the shared Docker
runtime test.
Repo-level tasks discover packages from `packaging/alpine/local/*/APKBUILD`. Repo-level tasks discover packages from `packaging/alpine/local/*/APKBUILD`.
Limit a task to one or more packages with: Limit a task to one or more packages with:
@@ -20,6 +22,7 @@ Limit a task to one or more packages with:
ALPINE_PACKAGE=<pkgname> mise run apk:build ALPINE_PACKAGE=<pkgname> mise run apk:build
ALPINE_PACKAGES="<pkg-a> <pkg-b>" mise run apk:build-all ALPINE_PACKAGES="<pkg-a> <pkg-b>" mise run apk:build-all
ALPINE_PACKAGE=<pkgname> mise run apk:test-install ALPINE_PACKAGE=<pkgname> mise run apk:test-install
ALPINE_PACKAGE=<pkgname> mise run apk:runtime-test
``` ```
For compiled software, put normal Alpine build logic in `build()`, `check()`, For compiled software, put normal Alpine build logic in `build()`, `check()`,
@@ -3,7 +3,7 @@ set -euo pipefail
repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}" repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}"
package_name="${PACKAGE_NAME:-$(basename "$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)")}" package_name="${PACKAGE_NAME:-$(basename "$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)")}"
alpine_version="${ALPINE_VERSION:-3.23}" alpine_version="${ALPINE_VERSION:-3.24}"
arch="${ALPINE_ARCH:-x86_64}" arch="${ALPINE_ARCH:-x86_64}"
case "${arch}" in case "${arch}" in
+77
View File
@@ -0,0 +1,77 @@
# Maintainer: Joachim Schlöffel <joachim.schloeffel@financial-service-plus.de>
pkgname=gitea
pkgver=1.27.1
pkgrel=2
pkgdesc="Self-hosted Git service written in Go"
url="https://about.gitea.com/"
arch="x86_64 aarch64"
license="MIT"
depends="git git-lfs gnupg"
makedepends="tar xz"
provides="cmd:gitea=$pkgver-r$pkgrel"
install="$pkgname.pre-install"
pkgusers="gitea"
pkggroups="www-data"
subpackages="
$pkgname-doc
$pkgname-openrc:_openrc:noarch
"
options="!check !strip !tracedeps"
case "$CARCH" in
x86_64)
_archive="$pkgname-$pkgver-linux-amd64.xz"
;;
aarch64)
_archive="$pkgname-$pkgver-linux-arm64.xz"
;;
esac
source="
$pkgname-$pkgver-linux-amd64.xz::https://github.com/go-gitea/gitea/releases/download/v$pkgver/gitea-$pkgver-linux-amd64.xz
$pkgname-$pkgver-linux-arm64.xz::https://github.com/go-gitea/gitea/releases/download/v$pkgver/gitea-$pkgver-linux-arm64.xz
$pkgname-src-$pkgver.tar.gz::https://github.com/go-gitea/gitea/releases/download/v$pkgver/gitea-src-$pkgver.tar.gz
gitea.ini
gitea.initd
"
builddir="$srcdir/gitea-src-$pkgver"
prepare() {
default_prepare
xz -dc "$srcdir/$_archive" > "$srcdir"/gitea
chmod 0755 "$srcdir"/gitea
}
package() {
local _dir
for _dir in gitea gitea/git gitea/data gitea/db gitea/custom; do
install -d -m 0750 -o gitea -g www-data \
"$pkgdir"/var/lib/$_dir
done
install -d -m 0755 -o gitea -g www-data "$pkgdir"/var/log/gitea
install -Dm755 "$srcdir"/gitea "$pkgdir"/usr/bin/gitea
install -Dm644 -o gitea -g www-data "$srcdir"/gitea.ini \
"$pkgdir"/etc/gitea/app.ini
chown gitea:www-data "$pkgdir"/etc/gitea
install -d -m 0755 "$pkgdir"/usr/share/webapps/gitea
cp -r "$builddir"/options "$builddir"/public "$builddir"/templates \
"$pkgdir"/usr/share/webapps/gitea/
install -Dm644 "$builddir"/LICENSE -t "$pkgdir"/usr/share/licenses/gitea/
}
_openrc() {
pkgdesc="$pkgdesc (OpenRC service)"
depends="$pkgname=$pkgver-r$pkgrel openrc"
install -Dm755 "$srcdir"/gitea.initd "$subpkgdir"/etc/init.d/gitea
}
sha512sums="
103a3af76a84d9a093aaed09f03519ae1f698609f3374d64bc0c3aaed00296e5bea8382e8b5a0115c56875d64b8dd8e69dea43093ecebcd87fd5298e533b6fa2 gitea-1.27.1-linux-amd64.xz
ffb9d13be03ada20a8b8d59c6e7885b4ba57a27f3f487920a61b2491e56c06eb8d4f21ff6fb32ea598535b3af66bb15347ed3e07df4eaf532ed4c63909e4caee gitea-1.27.1-linux-arm64.xz
19e9893a2e15de188ad4fb17f52c49c87884ff5c14d2fadf59213887f262f7200ae0a86af4d3c9488d1cded54864e08423b5058e60c694fbb235e8693736436d gitea-src-1.27.1.tar.gz
431184faffa8996873d92d7b0d16bc4b1a0178d264cd2928d1f49b13ad3e6470d9ede7a18c12112deeeb38f0647ccc0b012e98bcbd96e7b8496a3dc18f5b1fb7 gitea.ini
9474d707df8b049c93ec4642f71195adff699e1e812f315cac4295b3ab29eeb9ba8b83bf3307c50b04e072a4a9dc4c4f84ac490ee22291bd50015009795c1598 gitea.initd
"
+38
View File
@@ -0,0 +1,38 @@
# Gitea Alpine Package
Repackages upstream Gitea 1.27.0 Linux release binaries for `x86_64` and
`aarch64`.
The package follows Alpine's Gitea runtime layout:
- `/usr/bin/gitea`
- `/etc/gitea/app.ini`
- `/var/lib/gitea`
- `/var/log/gitea`
- `/usr/share/webapps/gitea`
Install the OpenRC service with:
```sh
apk add gitea gitea-openrc
rc-update add gitea default
rc-service gitea start
```
Refresh checksums:
```sh
ALPINE_PACKAGE=gitea mise run apk:checksum
```
Build:
```sh
ALPINE_PACKAGE=gitea mise run apk:build
```
Install-test local build:
```sh
ALPINE_PACKAGE=gitea SKIP_BUILD=1 mise run apk:test-install
```
+26
View File
@@ -0,0 +1,26 @@
# Configuration cheat sheet: https://docs.gitea.io/en-us/config-cheat-sheet/
RUN_USER = gitea
RUN_MODE = prod
[repository]
ROOT = /var/lib/gitea/git
SCRIPT_TYPE = sh
[server]
STATIC_ROOT_PATH = /usr/share/webapps/gitea
APP_DATA_PATH = /var/lib/gitea/data
LFS_START_SERVER = true
[database]
DB_TYPE = sqlite3
PATH = /var/lib/gitea/db/gitea.db
SSL_MODE = disable
[session]
PROVIDER = file
[log]
ROOT_PATH = /var/log/gitea
MODE = file
LEVEL = Info
+30
View File
@@ -0,0 +1,30 @@
#!/sbin/openrc-run
supervisor=supervise-daemon
name=gitea
command="/usr/bin/gitea"
command_user="${GITEA_USER:-gitea}"
command_args="web --config '${GITEA_CONF:-/etc/gitea/app.ini}'"
supervise_daemon_args="--env GITEA_WORK_DIR='${GITEA_WORK_DIR:-/var/lib/gitea}' --chdir '${GITEA_WORK_DIR:-/var/lib/gitea}' --stdout '${GITEA_LOG_FILE:-/var/log/gitea/http.log}' --stderr '${GITEA_LOG_FILE:-/var/log/gitea/http.log}'"
pidfile="/run/gitea.pid"
extra_started_commands="reopen_log"
capabilities="^cap_net_bind_service"
depend() {
use logger dns
need net
after firewall mysql postgresql
}
# https://github.com/go-gitea/gitea/issues/17976
# reload() {
# ebegin "Reloading ${RC_SVCNAME}"
# ${supervisor} ${RC_SVCNAME} --signal HUP --pidfile "${pidfile}"
# eend $?
# }
reopen_log() {
ebegin "Reopening logfile for ${RC_SVCNAME}"
${supervisor} ${RC_SVCNAME} --signal USR1 --pidfile "${pidfile}"
eend $?
}
+7
View File
@@ -0,0 +1,7 @@
#!/bin/sh
addgroup -S www-data 2>/dev/null
adduser -S -D -H -h /var/lib/gitea -s /sbin/nologin \
-G www-data -g gitea gitea 2>/dev/null
exit 0
+21
View File
@@ -0,0 +1,21 @@
#!/usr/bin/env bash
set -euo pipefail
apk add gitea gitea-doc gitea-openrc
test -x /usr/bin/gitea
test -f /etc/gitea/app.ini
test -d /var/lib/gitea
test -d /var/lib/gitea/git
test -d /var/lib/gitea/data
test -d /var/lib/gitea/db
test -d /var/log/gitea
test -d /usr/share/webapps/gitea/options
test -d /usr/share/webapps/gitea/public
test -d /usr/share/webapps/gitea/templates
test -f /etc/init.d/gitea
gitea --version
rc-update add gitea default || true
test -L /etc/runlevels/default/gitea
+53
View File
@@ -0,0 +1,53 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}"
# shellcheck source=scripts/apk/test-install-lib.sh
. "${repo_root}/scripts/apk/test-install-lib.sh"
apk_test_install_run "${repo_root}" "${PACKAGE_NAME:-gitea}" "${PACKAGE_VERSION:-1.27.0-r1}" <<'SCRIPT'
set -e
if [ -n "${ALPINE_REPOSITORY_URL}" ]; then
if [ -n "${ALPINE_REPOSITORY_KEY_URL}" ]; then
apk add --no-cache curl >/dev/null
cd /etc/apk/keys
curl -fsSLOJ "${ALPINE_REPOSITORY_KEY_URL}"
fi
printf "%s\n" "${ALPINE_REPOSITORY_URL}" >> /etc/apk/repositories
else
apk update
apk add "${PACKAGE_NAME}"
installed_before="$(apk list -I "${PACKAGE_NAME}" | awk "{print \$1}")"
printf "Installed repository package before local upgrade: %s\n" "${installed_before}"
if [ "${installed_before}" = "${PACKAGE_NAME}-${PACKAGE_VERSION}" ]; then
printf "default repository already has %s; upgrade path was not exercised\n" "${PACKAGE_VERSION}" >&2
exit 1
fi
cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/
printf "%s\n" /repo >> /etc/apk/repositories
fi
apk update
apk add --upgrade "${PACKAGE_NAME}" "${PACKAGE_NAME}-doc" "${PACKAGE_NAME}-openrc"
installed_after="$(apk list -I "${PACKAGE_NAME}" | awk "{print \$1}")"
printf "Installed package after local upgrade: %s\n" "${installed_after}"
test "${installed_after}" = "${PACKAGE_NAME}-${PACKAGE_VERSION}"
test -x /usr/bin/gitea
test -f /etc/gitea/app.ini
test -d /var/lib/gitea
test -d /var/lib/gitea/git
test -d /var/lib/gitea/data
test -d /var/lib/gitea/db
test -d /var/log/gitea
test -d /usr/share/webapps/gitea/options
test -d /usr/share/webapps/gitea/public
test -d /usr/share/webapps/gitea/templates
test -f /etc/init.d/gitea
gitea --version
rc-update add gitea default
test -L /etc/runlevels/default/gitea
SCRIPT
@@ -0,0 +1,3 @@
provider=github
repo=go-gitea/gitea
version_prefix=v
+98 -12
View File
@@ -1,18 +1,18 @@
# Maintainer: Joachim Schlöffel <me@joachim-schloeffel.com> # Maintainer: Joachim Schlöffel <mjoachim.schloeffel@financial-service-plus.de>
pkgname=greptimedb pkgname=greptimedb
pkgver=1.0.2 pkgver=1.1.4
pkgrel=0 pkgrel=0
pkgdesc="Cloud-native observability database for metrics, logs, and traces" pkgdesc="Cloud-native observability database for metrics, logs, and traces"
url="https://github.com/GreptimeTeam/greptimedb" url="https://github.com/GreptimeTeam/greptimedb"
arch="x86_64" arch="x86_64"
license="Apache-2.0" license="Apache-2.0"
depends="ca-certificates" depends="ca-certificates /bin/sh"
makedepends=" makedepends="
binutils binutils
cargo
clang clang
cmake cmake
coreutils coreutils
curl
lld lld
linux-headers linux-headers
make make
@@ -22,36 +22,122 @@ makedepends="
perl perl
protobuf protobuf
protobuf-dev protobuf-dev
rust rustup
zlib-dev zlib-dev
zlib-static zlib-static
zstd-dev zstd-dev
zstd-static zstd-static
" "
install="$pkgname.pre-install"
subpackages="
$pkgname-datanode-openrc:_openrc_datanode:noarch
$pkgname-docs:_docs:noarch
$pkgname-flownode-openrc:_openrc_flownode:noarch
$pkgname-frontend-openrc:_openrc_frontend:noarch
$pkgname-metasrv-openrc:_openrc_metasrv:noarch
$pkgname-standalone-openrc:_openrc_standalone:noarch
"
options="net" options="net"
source="$pkgname-$pkgver.tar.gz::https://github.com/GreptimeTeam/greptimedb/archive/refs/tags/v$pkgver.tar.gz" _dashboard_version="v0.12.0"
source="
$pkgname-$pkgver.tar.gz::https://github.com/GreptimeTeam/greptimedb/archive/refs/tags/v$pkgver.tar.gz
dashboard-$_dashboard_version.tar.gz::https://github.com/GreptimeTeam/dashboard/releases/download/$_dashboard_version/build.tar.gz
datanode.toml
flownode.toml
frontend.toml
greptimedb.datanode.confd
greptimedb.flownode.confd
greptimedb.frontend.confd
greptimedb.initd
greptimedb.metasrv.confd
greptimedb.standalone.confd
metasrv.toml
standalone.toml
"
export CARGO_HOME="$srcdir/cargo" _rust_toolchain="nightly-2026-03-21"
_cargo_profile="nightly"
export CARGO_HOME="${CARGO_HOME:-$srcdir/cargo}"
export CARGO_TARGET_DIR="${CARGO_TARGET_DIR:-$builddir/target}"
export RUSTUP_HOME="${RUSTUP_HOME:-$srcdir/rustup}"
export CARGO_BUILD_JOBS="${CARGO_BUILD_JOBS:-2}" export CARGO_BUILD_JOBS="${CARGO_BUILD_JOBS:-2}"
export CARGO_PROFILE_NIGHTLY_CODEGEN_UNITS="${CARGO_PROFILE_NIGHTLY_CODEGEN_UNITS:-16}"
export CARGO_PROFILE_NIGHTLY_DEBUG="${CARGO_PROFILE_NIGHTLY_DEBUG:-false}"
export CARGO_PROFILE_NIGHTLY_LTO="${CARGO_PROFILE_NIGHTLY_LTO:-thin}"
export LIBRARY_PATH="/usr/lib" export LIBRARY_PATH="/usr/lib"
prepare() {
default_prepare
if [ ! -d "$builddir"/src/servers/dashboard/dist ]; then
mv "$srcdir"/dist "$builddir"/src/servers/dashboard/dist
fi
rustup-init \
-y \
--no-modify-path \
--profile minimal \
--default-toolchain "$_rust_toolchain"
}
build() { build() {
cargo build \ "$CARGO_HOME"/bin/rustup run "$_rust_toolchain" cargo build \
--release \ --profile "$_cargo_profile" \
--locked \ --locked \
--bin greptime \ --bin greptime \
--features servers/dashboard --features servers/dashboard
} }
check() { check() {
"$builddir"/target/release/greptime --version "$CARGO_TARGET_DIR"/"$_cargo_profile"/greptime --version
} }
package() { package() {
install -Dm755 "$builddir"/target/release/greptime \ install -Dm755 "$CARGO_TARGET_DIR"/"$_cargo_profile"/greptime \
"$pkgdir"/usr/bin/greptime "$pkgdir"/usr/bin/greptime
local _config
for _config in datanode flownode frontend metasrv standalone; do
install -Dm644 "$srcdir"/$_config.toml \
"$pkgdir"/etc/greptimedb/$_config.toml
done
}
_openrc_service() {
local _service="$1"
pkgdesc="$pkgdesc (OpenRC $_service service)"
depends="$pkgname=$pkgver-r$pkgrel openrc"
install -Dm755 "$srcdir"/greptimedb.initd \
"$subpkgdir"/etc/init.d/greptimedb.$_service
install -Dm644 "$srcdir"/greptimedb.$_service.confd \
"$subpkgdir"/etc/conf.d/greptimedb.$_service
}
_openrc_datanode() { _openrc_service datanode; }
_openrc_flownode() { _openrc_service flownode; }
_openrc_frontend() { _openrc_service frontend; }
_openrc_metasrv() { _openrc_service metasrv; }
_openrc_standalone() { _openrc_service standalone; }
_docs() {
pkgdesc="$pkgdesc (configuration examples and reference)"
depends=""
mkdir -p "$subpkgdir"/usr/share/doc/$pkgname
cp -a "$builddir"/config "$subpkgdir"/usr/share/doc/$pkgname/
} }
sha512sums=" sha512sums="
7f4ac722b84a26816030e65d504b37a53edfca15de669a4f6ee7a903f1a29c8358dcc2376a0a6cfd9ded13b0c5d7550a6856b9b10dc8cd080c6b12970553a0ea greptimedb-1.0.2.tar.gz d60080a82a1dba52ab28d33ba1d9109bd047a6e598dbad17a3d92c82c6aad20b7fffd35cc20571829d8869360040af61195eeb97a14e08d8289e70663ee08664 greptimedb-1.1.4.tar.gz
4260acae5bed00a693dceffe9f53d0f8b25fd677b15638e951cf973dc29681f4bacde352c661a12bd78af7be9181a3740812f814fc3c4c8c87ea4eee6ee07e2d dashboard-v0.12.0.tar.gz
29cc3376753487b216748e3f85e12639830e1ac4a763e94f330f87c3651a8ef9de35732958311c0049e1b7cbb4e90a9e602b3aff43297fe088c5ce795a110a79 datanode.toml
52790808cb4f5cf0220ac2ab169b623fe76b6318d27d7f003e1197e850373cb915bfd40556098bcb7650f293d751039cb3bccbf9107bb160b8284887794ba975 flownode.toml
e3e19ab3c7a345ecf8cf0a507f7fc95dd3b036a4a797385cf77fcf1999f2e4f053042c7bbda8de73ed43ff72e87aad81e4ac6d4a34d01773bbc1f6d0d967d9f7 frontend.toml
313ed7d9ccd174b1869f3009e174266cdc414599e0b0f8307c8aaf2b73841eb36ce4c1b2f6244a0358b5a587a4edaa621b781fbd767835088b3fa13623fcc0df greptimedb.datanode.confd
daf8efacc8bf2b74abd9f4900f889585295b57333a8a562a722de0596d35f25d5f9149e0879f4140bfdf727caa59c3f55b1380212722df92c588d912275530b8 greptimedb.flownode.confd
e3e61b1df00f8172a3b1d4a0d37ed2574a8c5cd27676b4e2ce14d15ad8933d233baabe8da374f715d00cfaee26f665244c1ba00f70197fcc713c4e9af9c3229e greptimedb.frontend.confd
c00740aee566b161bbe3610e0e0d6e8340022055750e6778772262474ffd6484d9f58be2fd498beafe28d0943e259e2277930af691bedea7650726e6c8998881 greptimedb.initd
df495367d85844dcba99e5aa01e5a23fd14799b7521a72d9ea00d29fc0e5fbc5c5d06ee88e88d9637e260f8337249a39d2b0115de58da4899824d20bd844254a greptimedb.metasrv.confd
882a79e969cac42adfada22060e6507fb687755a6d266d6728154b3e4da5777d2eaf5ad9bc331ed050448249ca609e6a61977b624d9faf25d83ed975345452cf greptimedb.standalone.confd
8120ec338ebe1330d43b20d9b34a8f5f778ea13cb056febd3c8e9dc189d0de2380b90e5474a0990294d7004827c6133d44d2dd3e32d463b9259c47c82592d257 metasrv.toml
7e625a40460b363415b69e59142fd202c4dbb51296286e6afdeb94d6303e5bf097f2d83196bfeea8cf1182aa90ffd4a503a939426e7eeeea4c14b7242bb99ddb standalone.toml
" "
+71 -8
View File
@@ -1,32 +1,95 @@
# GreptimeDB Alpine Package # GreptimeDB Alpine Package
This package builds `greptime` from the upstream GreptimeDB source release. Builds `greptime` from the upstream source release and packages OpenRC service
subpackages plus `/etc/greptimedb` defaults.
The APKBUILD builds the release directly: Build command:
```sh ```sh
cargo build --release --locked --bin greptime --features servers/dashboard cargo build --profile nightly --locked --bin greptime --features servers/dashboard
``` ```
## Runtime Layout
Installs `/usr/bin/greptime` and component OpenRC packages:
- `greptimedb-docs`: upstream configuration examples and reference files from
`config/`
- `greptimedb-standalone-openrc`: `greptime standalone start`
- `greptimedb-metasrv-openrc`: `greptime metasrv start`
- `greptimedb-datanode-openrc`: `greptime datanode start`
- `greptimedb-flownode-openrc`: `greptime flownode start`
- `greptimedb-frontend-openrc`: `greptime frontend start`
Default TOML files are installed in `/etc/greptimedb`. Standalone ports:
- `127.0.0.1:4000`: HTTP API and dashboard
- `127.0.0.1:4001`: gRPC
- `127.0.0.1:4002`: MySQL
- `127.0.0.1:4003`: PostgreSQL
Configs bind to localhost by default. Upstream config examples are in
`/usr/share/doc/greptimedb/config`.
## OpenRC Usage
Standalone:
```sh
apk add greptimedb greptimedb-docs greptimedb-standalone-openrc
rc-update add greptimedb.standalone default
rc-service greptimedb.standalone start
```
Distributed components:
```sh
apk add \
greptimedb \
greptimedb-metasrv-openrc \
greptimedb-datanode-openrc \
greptimedb-flownode-openrc \
greptimedb-frontend-openrc
```
Wrapper settings in `/etc/conf.d/greptimedb.<component>`:
- `GREPTIMEDB_CONFIG`: config file path passed with `-c`
- `GREPTIMEDB_LOG_DIR`: component log directory passed with `--log-dir`
- `GREPTIMEDB_DATA_HOME`: data directory passed with `--data-home` where the
component supports it
- `GREPTIMEDB_WAL_DIR`: datanode WAL directory passed with `--wal-dir`
- `GREPTIMEDB_OPTS`: extra component arguments appended after package defaults
- `GREPTIMEDB_GLOBAL_OPTS`: arguments inserted before the component command
## Package Commands ## Package Commands
Refresh the source checksum after changing `pkgver`: Refresh checksums:
```sh ```sh
ALPINE_PACKAGE=greptimedb mise run apk:checksum ALPINE_PACKAGE=greptimedb mise run apk:checksum
``` ```
Build only this package: Build:
```sh ```sh
ALPINE_PACKAGE=greptimedb mise run apk:build ALPINE_PACKAGE=greptimedb mise run apk:build
``` ```
Install-test an existing build without recompiling: Install-test local build:
```sh ```sh
ALPINE_PACKAGE=greptimedb SKIP_BUILD=1 mise run apk:test-install ALPINE_PACKAGE=greptimedb SKIP_BUILD=1 mise run apk:test-install
``` ```
The full build can take close to an hour. Do not run it as part of lightweight Install-test published repository:
metadata or script checks.
```sh
ALPINE_PACKAGE=greptimedb \
SKIP_BUILD=1 \
ALPINE_REPOSITORY_URL=https://code.factoring.digital/api/packages/public/alpine/v3.24/alpine-packages \
ALPINE_REPOSITORY_KEY_URL=https://code.factoring.digital/api/packages/public/alpine/key \
mise run apk:test-install
```
Full builds take close to an hour.
@@ -0,0 +1,47 @@
node_id = 1
default_column_prefix = "greptime"
require_lease_before_startup = false
init_regions_in_background = false
init_regions_parallelism = 16
max_concurrent_queries = 0
[http]
addr = "127.0.0.1:4004"
timeout = "0s"
body_limit = "64MB"
[grpc]
bind_addr = "127.0.0.1:3001"
server_addr = "127.0.0.1:3001"
runtime_size = 8
max_recv_message_size = "512MB"
max_send_message_size = "512MB"
flight_compression = "arrow_ipc"
[grpc.tls]
mode = "disable"
[heartbeat]
interval = "3s"
retry_interval = "3s"
[meta_client]
metasrv_addrs = ["127.0.0.1:3002"]
timeout = "3s"
ddl_timeout = "10s"
connect_timeout = "1s"
tcp_nodelay = true
metadata_cache_max_capacity = 100000
metadata_cache_ttl = "10m"
metadata_cache_tti = "5m"
[wal]
dir = "/var/lib/greptimedb/datanode/wal"
[storage]
data_home = "/var/lib/greptimedb/datanode"
[logging]
dir = "/var/log/greptimedb/datanode"
level = "info"
enable_otlp_tracing = false
@@ -0,0 +1,38 @@
node_id = 1
[flow]
[flow.batching_mode]
[flow.batching_mode.frontend_tls]
[grpc]
bind_addr = "127.0.0.1:6800"
server_addr = "127.0.0.1:6800"
runtime_size = 2
max_recv_message_size = "512MB"
max_send_message_size = "512MB"
[http]
addr = "127.0.0.1:4005"
timeout = "0s"
body_limit = "64MB"
[meta_client]
metasrv_addrs = ["127.0.0.1:3002"]
timeout = "3s"
ddl_timeout = "10s"
connect_timeout = "1s"
tcp_nodelay = true
metadata_cache_max_capacity = 100000
metadata_cache_ttl = "10m"
metadata_cache_tti = "5m"
[heartbeat]
interval = "3s"
retry_interval = "3s"
[logging]
dir = "/var/log/greptimedb/flownode"
level = "info"
enable_otlp_tracing = false
@@ -0,0 +1,65 @@
default_timezone = "UTC"
default_column_prefix = "greptime"
[heartbeat]
interval = "18s"
retry_interval = "3s"
[http]
addr = "127.0.0.1:4000"
timeout = "0s"
body_limit = "64MB"
enable_cors = true
prom_validation_mode = "strict"
[grpc]
bind_addr = "127.0.0.1:4001"
server_addr = "127.0.0.1:4001"
runtime_size = 8
flight_compression = "arrow_ipc"
[grpc.tls]
mode = "disable"
[internal_grpc]
bind_addr = "127.0.0.1:4010"
server_addr = "127.0.0.1:4010"
runtime_size = 8
flight_compression = "arrow_ipc"
[internal_grpc.tls]
mode = "disable"
[mysql]
enable = true
addr = "127.0.0.1:4002"
runtime_size = 2
keep_alive = "0s"
prepared_stmt_cache_size = 10000
[mysql.tls]
mode = "disable"
[postgres]
enable = true
addr = "127.0.0.1:4003"
runtime_size = 2
keep_alive = "0s"
[postgres.tls]
mode = "disable"
[meta_client]
metasrv_addrs = ["127.0.0.1:3002"]
timeout = "3s"
ddl_timeout = "10s"
connect_timeout = "1s"
tcp_nodelay = true
metadata_cache_max_capacity = 100000
metadata_cache_ttl = "10m"
metadata_cache_tti = "5m"
[logging]
dir = "/var/log/greptimedb/frontend"
level = "info"
enable_otlp_tracing = false
@@ -0,0 +1,6 @@
# Defaults for "greptime datanode start".
GREPTIMEDB_CONFIG="/etc/greptimedb/datanode.toml"
GREPTIMEDB_LOG_DIR="/var/log/greptimedb/datanode"
GREPTIMEDB_DATA_HOME="/var/lib/greptimedb/datanode"
GREPTIMEDB_WAL_DIR="/var/lib/greptimedb/datanode/wal"
GREPTIMEDB_OPTS=""
@@ -0,0 +1,4 @@
# Defaults for "greptime flownode start".
GREPTIMEDB_CONFIG="/etc/greptimedb/flownode.toml"
GREPTIMEDB_LOG_DIR="/var/log/greptimedb/flownode"
GREPTIMEDB_OPTS=""
@@ -0,0 +1,4 @@
# Defaults for "greptime frontend start".
GREPTIMEDB_CONFIG="/etc/greptimedb/frontend.toml"
GREPTIMEDB_LOG_DIR="/var/log/greptimedb/frontend"
GREPTIMEDB_OPTS=""
+61
View File
@@ -0,0 +1,61 @@
#!/sbin/openrc-run
service_name="${RC_SVCNAME#greptimedb.}"
description="GreptimeDB ${service_name} service"
command="/usr/bin/greptime"
command_user="${GREPTIMEDB_USER:-greptimedb}:${GREPTIMEDB_GROUP:-greptimedb}"
command_background="yes"
pidfile="/run/greptimedb/${RC_SVCNAME}.pid"
output_log="${GREPTIMEDB_LOG:-/var/log/greptimedb/${RC_SVCNAME}.log}"
error_log="${GREPTIMEDB_ERRLOG:-/var/log/greptimedb/${RC_SVCNAME}.log}"
build_command_args() {
config_file="${GREPTIMEDB_CONFIG:-/etc/greptimedb/${service_name}.toml}"
log_dir="${GREPTIMEDB_LOG_DIR:-/var/log/greptimedb/${service_name}}"
data_home="${GREPTIMEDB_DATA_HOME:-/var/lib/greptimedb/${service_name}}"
wal_dir="${GREPTIMEDB_WAL_DIR:-/var/lib/greptimedb/${service_name}/wal}"
command_args="${GREPTIMEDB_GLOBAL_OPTS:-} ${service_name} start -c ${config_file} --log-dir ${log_dir}"
case "$service_name" in
datanode)
command_args="$command_args --data-home ${data_home} --wal-dir ${wal_dir}"
;;
metasrv|standalone)
command_args="$command_args --data-home ${data_home}"
;;
esac
command_args="$command_args ${GREPTIMEDB_OPTS:-}"
}
build_command_args
depend() {
need net
case "$service_name" in
datanode|flownode|frontend)
after greptimedb.metasrv
;;
esac
}
start_pre() {
checkpath -d -m 0755 -o "${GREPTIMEDB_USER:-greptimedb}:${GREPTIMEDB_GROUP:-greptimedb}" \
/run/greptimedb \
/var/log/greptimedb \
/var/lib/greptimedb \
"$log_dir"
case "$service_name" in
datanode)
checkpath -d -m 0750 -o "${GREPTIMEDB_USER:-greptimedb}:${GREPTIMEDB_GROUP:-greptimedb}" \
"$data_home" "$wal_dir"
;;
metasrv|standalone)
checkpath -d -m 0750 -o "${GREPTIMEDB_USER:-greptimedb}:${GREPTIMEDB_GROUP:-greptimedb}" \
"$data_home"
;;
esac
}
@@ -0,0 +1,5 @@
# Defaults for "greptime metasrv start".
GREPTIMEDB_CONFIG="/etc/greptimedb/metasrv.toml"
GREPTIMEDB_LOG_DIR="/var/log/greptimedb/metasrv"
GREPTIMEDB_DATA_HOME="/var/lib/greptimedb/metasrv"
GREPTIMEDB_OPTS=""
+7
View File
@@ -0,0 +1,7 @@
#!/bin/sh
addgroup -S greptimedb 2>/dev/null
adduser -S -D -H -h /var/lib/greptimedb -s /sbin/nologin \
-G greptimedb -g greptimedb greptimedb 2>/dev/null
exit 0
@@ -0,0 +1,5 @@
# Defaults for "greptime standalone start".
GREPTIMEDB_CONFIG="/etc/greptimedb/standalone.toml"
GREPTIMEDB_LOG_DIR="/var/log/greptimedb/standalone"
GREPTIMEDB_DATA_HOME="/var/lib/greptimedb/standalone"
GREPTIMEDB_OPTS=""
@@ -0,0 +1,24 @@
data_home = "/var/lib/greptimedb/metasrv"
store_addrs = []
store_key_prefix = ""
backend = "memory_store"
selector = "round_robin"
enable_region_failover = false
region_failure_detector_initialization_delay = "10m"
allow_region_failover_on_local_wal = false
node_max_idle_time = "24hours"
[http]
addr = "127.0.0.1:3000"
timeout = "0s"
body_limit = "64MB"
[grpc]
bind_addr = "127.0.0.1:3002"
server_addr = "127.0.0.1:3002"
runtime_size = 8
[logging]
dir = "/var/log/greptimedb/metasrv"
level = "info"
enable_otlp_tracing = false
+23
View File
@@ -0,0 +1,23 @@
#!/usr/bin/env bash
set -euo pipefail
apk add greptimedb \
greptimedb-datanode-openrc \
greptimedb-docs \
greptimedb-flownode-openrc \
greptimedb-frontend-openrc \
greptimedb-metasrv-openrc \
greptimedb-standalone-openrc
test -x /usr/bin/greptime
test -d /etc/greptimedb
test -f /etc/greptimedb/standalone.toml
test -f /etc/conf.d/greptimedb.standalone
test -f /etc/init.d/greptimedb.standalone
test -f /usr/share/doc/greptimedb/config/config.md
test -f /usr/share/doc/greptimedb/config/standalone.example.toml
greptime --version
rc-update add greptimedb.standalone default || true
test -L /etc/runlevels/default/greptimedb.standalone
@@ -2,46 +2,37 @@
set -euo pipefail set -euo pipefail
repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}" repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}"
package_name="${PACKAGE_NAME:-greptimedb}" # shellcheck source=scripts/apk/test-install-lib.sh
alpine_version="${ALPINE_VERSION:-3.23}" . "${repo_root}/scripts/apk/test-install-lib.sh"
arch="${ALPINE_ARCH:-x86_64}"
case "${arch}" in apk_test_install_run "${repo_root}" "${PACKAGE_NAME:-greptimedb}" "${PACKAGE_VERSION:-}" <<'SCRIPT'
x86_64)
platform="${ALPINE_TEST_PLATFORM:-linux/amd64}"
;;
aarch64)
platform="${ALPINE_TEST_PLATFORM:-linux/arm64}"
;;
*)
printf 'unsupported Alpine architecture: %s\n' "${arch}" >&2
exit 2
;;
esac
if [[ "${SKIP_BUILD:-0}" != "1" ]]; then
ALPINE_PACKAGE="${package_name}" "${repo_root}/scripts/apk/build.sh" build "${arch}"
fi
if [[ ! -d "${repo_root}/packages/local/${arch}" ]]; then
printf 'missing local repository: packages/local/%s\n' "${arch}" >&2
printf 'run: ALPINE_PACKAGE=%s mise run apk:build\n' "${package_name}" >&2
exit 1
fi
docker run --rm --platform "${platform}" \
-e "ALPINE_ARCH=${arch}" \
-e "PACKAGE_NAME=${package_name}" \
-v "${repo_root}/packages/local:/repo:ro" \
"alpine:${alpine_version}" \
sh -lc '
set -e set -e
cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/ if [ -n "${ALPINE_REPOSITORY_URL}" ]; then
printf "%s\n" /repo >> /etc/apk/repositories if [ -n "${ALPINE_REPOSITORY_KEY_URL}" ]; then
apk add --no-cache curl >/dev/null
cd /etc/apk/keys
curl -fsSLOJ "${ALPINE_REPOSITORY_KEY_URL}"
fi
printf "%s\n" "${ALPINE_REPOSITORY_URL}" >> /etc/apk/repositories
else
cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/
printf "%s\n" /repo >> /etc/apk/repositories
fi
apk update apk update
apk add "${PACKAGE_NAME}" apk add \
"${PACKAGE_NAME}" \
"${PACKAGE_NAME}-datanode-openrc" \
"${PACKAGE_NAME}-docs" \
"${PACKAGE_NAME}-flownode-openrc" \
"${PACKAGE_NAME}-frontend-openrc" \
"${PACKAGE_NAME}-metasrv-openrc" \
"${PACKAGE_NAME}-standalone-openrc"
test -x /usr/bin/greptime test -x /usr/bin/greptime
greptime --version greptime --version
' ls -1 /etc/greptimedb
test -f "/usr/share/doc/${PACKAGE_NAME}/config/config.md"
test -f "/usr/share/doc/${PACKAGE_NAME}/config/standalone.example.toml"
find /etc/init.d -maxdepth 1 -name "greptimedb.*" -print | sort
SCRIPT
@@ -0,0 +1,46 @@
default_timezone = "UTC"
default_column_prefix = "greptime"
init_regions_in_background = false
init_regions_parallelism = 16
max_concurrent_queries = 0
[http]
addr = "127.0.0.1:4000"
timeout = "0s"
body_limit = "64MB"
enable_cors = true
prom_validation_mode = "strict"
[grpc]
bind_addr = "127.0.0.1:4001"
runtime_size = 8
[grpc.tls]
mode = "disable"
[mysql]
enable = true
addr = "127.0.0.1:4002"
runtime_size = 2
keep_alive = "0s"
prepared_stmt_cache_size = 10000
[mysql.tls]
mode = "disable"
[postgres]
enable = true
addr = "127.0.0.1:4003"
runtime_size = 2
keep_alive = "0s"
[postgres.tls]
mode = "disable"
[storage]
data_home = "/var/lib/greptimedb/standalone"
[logging]
dir = "/var/log/greptimedb/standalone"
level = "info"
enable_otlp_tracing = false
@@ -0,0 +1,3 @@
provider=github
repo=GreptimeTeam/greptimedb
version_prefix=v
+74
View File
@@ -0,0 +1,74 @@
# Maintainer: Joachim Schlöffel <joachim.schloeffel@financial-service-plus.de>
pkgname=lavinmq
pkgver=2.9.1
pkgrel=2
pkgdesc="High-performance AMQP and MQTT message queue server"
url="https://github.com/cloudamqp/lavinmq"
arch="x86_64"
license="Apache-2.0"
depends="ca-certificates /bin/sh"
makedepends="
crystal>=1.20.1
curl
gc-dev
help2man
libevent-dev
lz4-dev
make
openssl
openssl-dev
pcre2-dev
shards
tar
yaml-dev
"
install="$pkgname.pre-install"
pkgusers="lavinmq"
pkggroups="lavinmq"
subpackages="
$pkgname-doc
$pkgname-openrc:_openrc:noarch
"
options="net"
source="
$pkgname-$pkgver.tar.gz::https://github.com/cloudamqp/lavinmq/archive/refs/tags/v$pkgver.tar.gz
lavinmq.confd
lavinmq.initd
"
export CRYSTAL_CACHE_DIR="${CRYSTAL_CACHE_DIR:-$srcdir/crystal-cache}"
export SHARDS_CACHE_PATH="${SHARDS_CACHE_PATH:-$srcdir/shards-cache}"
build() {
make
make man
}
check() {
bin/lavinmq -v
bin/lavinmqctl --version
bin/lavinmqperf --version
}
package() {
make DESTDIR="$pkgdir" install
rm -r "$pkgdir"/lib/systemd "$pkgdir"/usr/lib/sysusers.d
rmdir "$pkgdir"/lib "$pkgdir"/usr/lib
install -d -m 0750 -o lavinmq -g lavinmq "$pkgdir"/var/lib/lavinmq
}
_openrc() {
pkgdesc="$pkgdesc (OpenRC service)"
depends="$pkgname=$pkgver-r$pkgrel openrc"
install -Dm755 "$srcdir"/lavinmq.initd \
"$subpkgdir"/etc/init.d/lavinmq
install -Dm644 "$srcdir"/lavinmq.confd \
"$subpkgdir"/etc/conf.d/lavinmq
}
sha512sums="
5f88de7a1e093b1f6e2ead5c340140bd489a99ca8adfa9f40052148490d0bdf8ff1e2dad67727e9799ad1f942755df01525e63d24b0901684a743f43c42110b9 lavinmq-2.9.1.tar.gz
62a609d50f28db960098c4c84ce4f1dad78413366a9a9aca18fe321114d687be3bf7b71924d4ace69bd74383c5ac40d2ee09ae0eef9c1bfe653b97448e42e110 lavinmq.confd
1853196e70297b5c4a2207fde50df735620cf6d99c4994644fd676bffaf863d67300ad7ae771c4bbb86fce1a0485c2a7968cf912c5f5bb878e08b15e5a28ba1b lavinmq.initd
"
+72
View File
@@ -0,0 +1,72 @@
# LavinMQ Alpine Package
Builds LavinMQ from the upstream source release for `x86_64` and packages the
OpenRC service plus `/etc/lavinmq` defaults.
Build command:
```sh
make
```
LavinMQ 2.9.1 requires Crystal 1.20.1 or newer, so build with Alpine 3.24 or
newer.
## Runtime Layout
Installs:
- `lavinmq`
- `lavinmqctl`
- `lavinmqperf`
- `/etc/lavinmq/lavinmq.ini`
- `/var/lib/lavinmq`
Default ports:
- `5672`: AMQP
- `15672`: management UI
## OpenRC Usage
```sh
apk add lavinmq lavinmq-doc lavinmq-openrc
rc-update add lavinmq default
rc-service lavinmq start
```
Wrapper settings in `/etc/conf.d/lavinmq`:
- `LAVINMQ_CONFIG`: config file path passed with `--config`
- `LAVINMQ_DATA_DIR`: data directory passed with `-D`
- `LAVINMQ_OPTS`: extra LavinMQ arguments appended after package defaults
## Package Commands
Refresh checksums:
```sh
ALPINE_PACKAGE=lavinmq mise run apk:checksum
```
Build:
```sh
ALPINE_PACKAGE=lavinmq mise run apk:build
```
Install-test local build:
```sh
ALPINE_PACKAGE=lavinmq SKIP_BUILD=1 mise run apk:test-install
```
Install-test published repository:
```sh
ALPINE_PACKAGE=lavinmq \
SKIP_BUILD=1 \
ALPINE_REPOSITORY_URL=https://code.factoring.digital/api/packages/public/alpine/v3.24/alpine-packages \
ALPINE_REPOSITORY_KEY_URL=https://code.factoring.digital/api/packages/public/alpine/key \
mise run apk:test-install
```
@@ -0,0 +1,4 @@
# Defaults for LavinMQ.
LAVINMQ_CONFIG="/etc/lavinmq/lavinmq.ini"
LAVINMQ_DATA_DIR="/var/lib/lavinmq"
LAVINMQ_OPTS=""
+28
View File
@@ -0,0 +1,28 @@
#!/sbin/openrc-run
description="LavinMQ message queue service"
command="/usr/bin/lavinmq"
command_user="${LAVINMQ_USER:-lavinmq}:${LAVINMQ_GROUP:-lavinmq}"
command_background="yes"
pidfile="/run/lavinmq/lavinmq.pid"
output_log="${LAVINMQ_LOG:-/var/log/lavinmq/lavinmq.log}"
error_log="${LAVINMQ_ERRLOG:-/var/log/lavinmq/lavinmq.log}"
config_file="${LAVINMQ_CONFIG:-/etc/lavinmq/lavinmq.ini}"
data_dir="${LAVINMQ_DATA_DIR:-/var/lib/lavinmq}"
command_args="-D ${data_dir} --config ${config_file} ${LAVINMQ_OPTS:-}"
depend() {
need net
}
start_pre() {
local service_owner="${LAVINMQ_USER:-lavinmq}:${LAVINMQ_GROUP:-lavinmq}"
checkpath -d -m 0755 -o "$service_owner" \
/run/lavinmq \
/var/log/lavinmq
checkpath -d -m 0750 -o "$service_owner" "$data_dir"
checkpath -f -m 0640 -o "$service_owner" "$data_dir"/.lock
}
+7
View File
@@ -0,0 +1,7 @@
#!/bin/sh
addgroup -S lavinmq 2>/dev/null
adduser -S -D -H -h /var/lib/lavinmq -s /sbin/nologin \
-G lavinmq -g lavinmq lavinmq 2>/dev/null
exit 0
+21
View File
@@ -0,0 +1,21 @@
#!/usr/bin/env bash
set -euo pipefail
apk add lavinmq lavinmq-doc lavinmq-openrc
test -x /usr/bin/lavinmq
test -x /usr/bin/lavinmqctl
test -x /usr/bin/lavinmqperf
test -f /etc/lavinmq/lavinmq.ini
test -d /var/lib/lavinmq
test "$(stat -c '%U:%G %a' /var/lib/lavinmq)" = "lavinmq:lavinmq 750"
test -f /etc/conf.d/lavinmq
test -f /etc/init.d/lavinmq
test -f /usr/share/doc/lavinmq/README.md
lavinmq -v
lavinmqctl --version
lavinmqperf --version
rc-update add lavinmq default || true
test -L /etc/runlevels/default/lavinmq
+42
View File
@@ -0,0 +1,42 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}"
# shellcheck source=scripts/apk/test-install-lib.sh
. "${repo_root}/scripts/apk/test-install-lib.sh"
apk_test_install_run "${repo_root}" "${PACKAGE_NAME:-lavinmq}" "${PACKAGE_VERSION:-}" <<'SCRIPT'
set -e
if [ -n "${ALPINE_REPOSITORY_URL}" ]; then
if [ -n "${ALPINE_REPOSITORY_KEY_URL}" ]; then
apk add --no-cache curl >/dev/null
cd /etc/apk/keys
curl -fsSLOJ "${ALPINE_REPOSITORY_KEY_URL}"
fi
printf "%s\n" "${ALPINE_REPOSITORY_URL}" >> /etc/apk/repositories
else
cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/
printf "%s\n" /repo >> /etc/apk/repositories
fi
apk update
apk add "${PACKAGE_NAME}" "${PACKAGE_NAME}-doc" "${PACKAGE_NAME}-openrc"
test -x /usr/bin/lavinmq
test -x /usr/bin/lavinmqctl
test -x /usr/bin/lavinmqperf
test -f /etc/lavinmq/lavinmq.ini
test -d /var/lib/lavinmq
test "$(stat -c "%U:%G %a" /var/lib/lavinmq)" = "lavinmq:lavinmq 750"
test -f /etc/conf.d/lavinmq
test -f /etc/init.d/lavinmq
test -f /usr/share/doc/lavinmq/README.md
test -f /usr/share/doc/lavinmq/changelog
lavinmq -v
lavinmqctl --version
lavinmqperf --version
rc-update add lavinmq default
test -L /etc/runlevels/default/lavinmq
SCRIPT
@@ -0,0 +1,3 @@
provider=github
repo=cloudamqp/lavinmq
version_prefix=v
+7 -7
View File
@@ -1,7 +1,7 @@
# Maintainer: Joachim Schlöffel <me@joachim-schloeffel.com> # Maintainer: Joachim Schlöffel <joachim.schloeffel@financial-service-plus.de>
pkgname=seaweedfs pkgname=seaweedfs
pkgver=4.31 pkgver=4.41
pkgrel=3 pkgrel=0
pkgdesc="Distributed storage system for object storage, file systems, and Iceberg tables" pkgdesc="Distributed storage system for object storage, file systems, and Iceberg tables"
url="https://github.com/seaweedfs/seaweedfs" url="https://github.com/seaweedfs/seaweedfs"
arch="x86_64 aarch64" arch="x86_64 aarch64"
@@ -109,15 +109,15 @@ _bashcomp() {
} }
sha512sums=" sha512sums="
60c758d6d565d0cbc533e4e5677186a4700d48be12ebbd2bd1c6b4bcf38f687d0ab1f66e0953c8a27c663549cdbae73e5fd7eda74bb422c20e10e0d0850b5ead seaweedfs-4.31-linux-amd64.tar.gz 51810779863e7b5578ef1a236af137f2ef79e44b7d8f10b5b36f6d45fa002ae8c6ad92f18e7fefdff8f7a4ec5c29acea13d757faf74e26f0a2e3914680a03092 seaweedfs-4.41-linux-amd64.tar.gz
93c7539fe15a0aa6192d26ac2360003961f0643e302d910179d02341b10a7243df776294fb1b0134ec2a2a9596b1abc3ce9ab701f9bc3d78f2b965ea464a4b18 seaweedfs-4.31-linux-arm64.tar.gz 20b7504c2efcfaab86e92ad336715f80e3653dc833e20c56f7cde545b57488374648d5155e47b4faaa95df92311a0675d368baa01e75a717c788a304655b29c7 seaweedfs-4.41-linux-arm64.tar.gz
b6ce09d6d83dd70e2797a185171eea3587436fb024a99b4998f714b713244d6f768ef59f67c9b7251650d4f19d414eea231eab92099763d85cd92e41cb2bdc3f credential.toml b6ce09d6d83dd70e2797a185171eea3587436fb024a99b4998f714b713244d6f768ef59f67c9b7251650d4f19d414eea231eab92099763d85cd92e41cb2bdc3f credential.toml
7105de7053654b8c0502521ce58585915fc831c3152801e1db02b1c5214dc3c3ed31f4fc18000665d8338c7a10ffbf0d248368bef2ef3a6d37d46cd856398366 example-credential.toml 7105de7053654b8c0502521ce58585915fc831c3152801e1db02b1c5214dc3c3ed31f4fc18000665d8338c7a10ffbf0d248368bef2ef3a6d37d46cd856398366 example-credential.toml
6213e9cff227d66a7a04237d15e2f77904f1bcdf5709fd985c1e12fe4aca0d0327db6997d567303eff47dabec3650db2a6d874b03adda41b239e04ee0c3557ee example-filer.toml 9e6401387698832cb4aae0876ef3e237c9b70af17db7563ed641ba40c81af99f1d6c22281bafa64fff7ee8d2c89f16ccac1322ea31c9a02b545faa4e09f08549 example-filer.toml
e5753bd0bcc60dc84428c40ba556c08acae61dec083a5b76640125f637532e7c5759a72cdfd95114222a7a0901a916ec3c4d12f306853cfca0fe9a0b1857893e example-master.toml e5753bd0bcc60dc84428c40ba556c08acae61dec083a5b76640125f637532e7c5759a72cdfd95114222a7a0901a916ec3c4d12f306853cfca0fe9a0b1857893e example-master.toml
2c200c28172a5d0b1c80ab28e849287e7af8d103355638fd3183b8614d3e2b1b3482132522663f7c6d844e10e13b8c6e23fb5fba0dec2cc83de45c2f17b33477 example-notification.toml 2c200c28172a5d0b1c80ab28e849287e7af8d103355638fd3183b8614d3e2b1b3482132522663f7c6d844e10e13b8c6e23fb5fba0dec2cc83de45c2f17b33477 example-notification.toml
4b507540d57799e42ec0ee84073c6fa32c577a2f4a98bf66ee7302355080c63c65d70709115185debdee3c957e9294e79a8e461347d7148af7fdd368dc548af6 example-replication.toml 4b507540d57799e42ec0ee84073c6fa32c577a2f4a98bf66ee7302355080c63c65d70709115185debdee3c957e9294e79a8e461347d7148af7fdd368dc548af6 example-replication.toml
a0f307bc73b1aa03653c42c22a1fc704640cbd86957a417f947fe33356e03734c33782777cb1d6cb17360fc6b3930ffbe1386f89123e9dc3c21468210418aae2 example-security.toml 6951e1110d458238b0ef1905c4c6bb874d06f1c18b83dd8e1742534806b8db68b4410a664bf53085781e5d4d35e87941279d9c7398529ee707bb99def5055591 example-security.toml
70069f97edf261a2cd0669dd60adad80533609a25d7429254e0c3322d7e80337f5ff69a5581bc39e6a15442098d14d610ce5f0cb14f02c461c8d3dd440b22c56 example-shell.toml 70069f97edf261a2cd0669dd60adad80533609a25d7429254e0c3322d7e80337f5ff69a5581bc39e6a15442098d14d610ce5f0cb14f02c461c8d3dd440b22c56 example-shell.toml
be5771a5e1bf626c53f9dffbfa2a400d9b8f9626d55a7b61dcd853753561989427ba872a2638a5e6343f44dea6790678483bd29101d6495dbbfcd3029947b9a7 filer.toml be5771a5e1bf626c53f9dffbfa2a400d9b8f9626d55a7b61dcd853753561989427ba872a2638a5e6343f44dea6790678483bd29101d6495dbbfcd3029947b9a7 filer.toml
2cd6c73a5e23e0395b6f099dcc3acf9280cbb3e13f54408571e91741c4e6b0dad85f6d4e5a92f23ad541bad57ce295c28bb8450fe11da35acbd4da25848f61e5 master.toml 2cd6c73a5e23e0395b6f099dcc3acf9280cbb3e13f54408571e91741c4e6b0dad85f6d4e5a92f23ad541bad57ce295c28bb8450fe11da35acbd4da25848f61e5 master.toml
+131
View File
@@ -0,0 +1,131 @@
# SeaweedFS Alpine Package
Repackages official SeaweedFS 4.39 Linux release tarballs for `x86_64` and
`aarch64`.
## Package Commands
Refresh generated sources:
```sh
ALPINE_PACKAGE=seaweedfs mise run apk:update-generated
ALPINE_PACKAGE=seaweedfs mise run apk:checksum
```
Build:
```sh
ALPINE_PACKAGE=seaweedfs mise run apk:build
```
Install-test local build:
```sh
ALPINE_PACKAGE=seaweedfs SKIP_BUILD=1 mise run apk:test-install
```
## Install Node Roles
Single-node install:
```sh
apk add seaweedfs \
seaweedfs-master-openrc \
seaweedfs-volume-openrc \
seaweedfs-filer-openrc
```
Role-specific installs:
```sh
apk add seaweedfs seaweedfs-master-openrc
apk add seaweedfs seaweedfs-volume-openrc
apk add seaweedfs seaweedfs-filer-openrc
```
Available OpenRC role packages:
```text
seaweedfs-master-openrc -> /etc/init.d/seaweedfs.master
seaweedfs-volume-openrc -> /etc/init.d/seaweedfs.volume
seaweedfs-filer-openrc -> /etc/init.d/seaweedfs.filer
seaweedfs-s3-openrc -> /etc/init.d/seaweedfs.s3
seaweedfs-webdav-openrc -> /etc/init.d/seaweedfs.webdav
seaweedfs-sftp-openrc -> /etc/init.d/seaweedfs.sftp
seaweedfs-admin-openrc -> /etc/init.d/seaweedfs.admin
seaweedfs-worker-openrc -> /etc/init.d/seaweedfs.worker
```
Replace Alpine's old generic OpenRC package before installing a role split:
```sh
apk del seaweedfs-openrc
apk add seaweedfs seaweedfs-master-openrc
```
## Configure Services
Runtime paths:
```text
/usr/bin/weed
/etc/seaweedfs/*.toml
/etc/conf.d/seaweedfs.*
/etc/init.d/seaweedfs.*
```
Edit `/etc/conf.d/seaweedfs.<role>` for flags and `/etc/seaweedfs/*.toml` for
SeaweedFS config. Upstream examples:
```text
/usr/share/doc/seaweedfs/examples/
```
Enable services:
```sh
rc-update add seaweedfs.master default
rc-service seaweedfs.master start
rc-update add seaweedfs.volume default
rc-service seaweedfs.volume start
rc-update add seaweedfs.filer default
rc-service seaweedfs.filer start
```
Check status:
```sh
weed version
rc-service seaweedfs.master status
```
## Optional Packages
Docs and examples:
```sh
apk add seaweedfs-doc
```
Bash completion:
```sh
apk add bash-completion seaweedfs-bash-completion
```
## Upgrade Or Pin
Upgrade:
```sh
apk upgrade seaweedfs
rc-service seaweedfs.master restart
```
Pin:
```sh
apk add seaweedfs=4.39-r0
```
@@ -366,6 +366,21 @@ healthcheck_enabled = false
# increase the value is recommend, be sure the value in Elastic is greater or equal here # increase the value is recommend, be sure the value in Elastic is greater or equal here
index.max_result_window = 10000 index.max_result_window = 10000
# for Elasticsearch 8.x clusters
[elastic8]
enabled = false
servers = [
"http://localhost1:9200",
"http://localhost2:9200",
"http://localhost3:9200",
]
username = ""
password = ""
sniff_enabled = false
healthcheck_enabled = false
# increase the value is recommend, be sure the value in Elastic is greater or equal here
index.max_result_window = 10000
[arangodb] # in development dont use it [arangodb] # in development dont use it
enabled = false enabled = false
@@ -4,7 +4,16 @@
# /etc/seaweedfs/security.toml # /etc/seaweedfs/security.toml
# this file is read by master, volume server, filer, and worker # this file is read by master, volume server, filer, and worker
# comma separated origins allowed to make requests to the filer and s3 gateway. # Any value below can also be supplied as an environment variable instead of
# living in this file: prefix the key with WEED_, upper-case it, and replace
# "." with "_". This is the recommended way to inject the secrets in here from
# a Kubernetes Secret (env valueFrom.secretKeyRef) rather than a ConfigMap.
# The JWT signing keys map to:
# WEED_JWT_SIGNING_KEY, WEED_JWT_SIGNING_READ_KEY (master <-> volume)
# WEED_JWT_FILER_SIGNING_KEY, WEED_JWT_FILER_SIGNING_READ_KEY (s3/clients <-> filer)
# A set env var wins over the file, so the file can stay empty (or absent).
# comma separated origins allowed to make requests to the filer and s3 gateway.
# enter in this format: https://domain.com, or http://localhost:port # enter in this format: https://domain.com, or http://localhost:port
[cors.allowed_origins] [cors.allowed_origins]
values = "*" values = "*"
+37
View File
@@ -0,0 +1,37 @@
#!/usr/bin/env bash
set -euo pipefail
apk add seaweedfs \
seaweedfs-doc \
bash-completion \
seaweedfs-master-openrc \
seaweedfs-volume-openrc \
seaweedfs-filer-openrc
test -x /usr/bin/weed
test -d /etc/seaweedfs
test -f /etc/seaweedfs/master.toml
test -f /etc/seaweedfs/filer.toml
test -f /etc/conf.d/seaweedfs.master
test -f /etc/conf.d/seaweedfs.volume
test -f /etc/conf.d/seaweedfs.filer
test -f /etc/init.d/seaweedfs.master
test -f /etc/init.d/seaweedfs.volume
test -f /etc/init.d/seaweedfs.filer
test -d /usr/share/doc/seaweedfs/examples
test -f /usr/share/doc/seaweedfs/examples/master.toml
test -f /usr/share/bash-completion/completions/weed
weed version
rc-update add seaweedfs.master default || true
rc-update add seaweedfs.volume default || true
rc-update add seaweedfs.filer default || true
rc-service seaweedfs.master start
rc-service seaweedfs.volume start
rc-service seaweedfs.filer start
rc-service seaweedfs.master status
rc-service seaweedfs.volume status
rc-service seaweedfs.filer status
@@ -2,38 +2,10 @@
set -euo pipefail set -euo pipefail
repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}" repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}"
package_name="${PACKAGE_NAME:-seaweedfs}" # shellcheck source=scripts/apk/test-install-lib.sh
alpine_version="${ALPINE_VERSION:-3.23}" . "${repo_root}/scripts/apk/test-install-lib.sh"
arch="${ALPINE_ARCH:-x86_64}"
case "${arch}" in apk_test_install_run "${repo_root}" "${PACKAGE_NAME:-seaweedfs}" "${PACKAGE_VERSION:-}" <<'SCRIPT'
x86_64)
platform="${ALPINE_TEST_PLATFORM:-linux/amd64}"
;;
aarch64)
platform="${ALPINE_TEST_PLATFORM:-linux/arm64}"
;;
*)
printf 'unsupported Alpine architecture: %s\n' "${arch}" >&2
exit 2
;;
esac
if [[ "${SKIP_BUILD:-0}" != "1" ]]; then
ALPINE_PACKAGE="${package_name}" "${repo_root}/scripts/apk/build.sh" build "${arch}"
fi
if [[ ! -d "${repo_root}/packages/local/${arch}" ]]; then
printf 'missing local repository: packages/local/%s\n' "${arch}" >&2
printf 'run: ALPINE_PACKAGE=%s mise run apk:build\n' "${package_name}" >&2
exit 1
fi
docker run --rm --platform "${platform}" \
-e "ALPINE_ARCH=${arch}" \
-v "${repo_root}/packages/local:/repo:ro" \
"alpine:${alpine_version}" \
sh -lc '
set -e set -e
cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/ cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/
@@ -70,4 +42,4 @@ docker run --rm --platform "${platform}" \
test -d /usr/share/doc/seaweedfs/examples test -d /usr/share/doc/seaweedfs/examples
test -f /usr/share/doc/seaweedfs/examples/master.toml test -f /usr/share/doc/seaweedfs/examples/master.toml
test -f /usr/share/bash-completion/completions/weed test -f /usr/share/bash-completion/completions/weed
' SCRIPT
@@ -1,15 +1,41 @@
#!/usr/bin/env bash #!/usr/bin/env bash
set -euo pipefail set -euo pipefail
repo_root="${REPO_ROOT:-$(cd "$(dirname "${BASH_SOURCE[0]}")/../../../../.." && pwd)}"
package_dir="${PACKAGE_DIR:-$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)}" package_dir="${PACKAGE_DIR:-$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)}"
configs=(credential filer master notification replication security shell) configs=(credential filer master notification replication security shell)
pkgver="$(
awk -F= '$1 == "pkgver" { print $2; exit }' "${package_dir}/APKBUILD"
)"
tmpdir="$(mktemp -d)"
cleanup() {
rm -rf "${tmpdir}"
}
trap cleanup EXIT
case "$(uname -m)" in
x86_64)
archive="linux_amd64.tar.gz"
;;
aarch64|arm64)
archive="linux_arm64.tar.gz"
;;
*)
printf 'unsupported host architecture for SeaweedFS generated sources: %s\n' "$(uname -m)" >&2
exit 2
;;
esac
curl -fsSL \
-o "${tmpdir}/${archive}" \
"https://github.com/seaweedfs/seaweedfs/releases/download/${pkgver}/${archive}"
tar -xzf "${tmpdir}/${archive}" -C "${tmpdir}" weed
for config in "${configs[@]}"; do for config in "${configs[@]}"; do
"${repo_root}/bin/weed" scaffold -config "${config}" 2>/dev/null \ "${tmpdir}/weed" scaffold -config "${config}" 2>/dev/null \
> "${package_dir}/example-${config}.toml" > "${package_dir}/example-${config}.toml"
done done
"${repo_root}/bin/weed" autocomplete bash 2>/dev/null \ "${tmpdir}/weed" autocomplete bash 2>/dev/null \
| sed -E 's#complete -C "?[^"]*/weed"? weed#complete -C /usr/bin/weed weed#' \ | sed -E 's#complete -C "?[^"]*/weed"? weed#complete -C /usr/bin/weed weed#' \
> "${package_dir}/weed.bash-completion" > "${package_dir}/weed.bash-completion"
@@ -0,0 +1,3 @@
provider=github
repo=seaweedfs/seaweedfs
version_prefix=none
+8 -2
View File
@@ -1,4 +1,4 @@
ARG ALPINE_VERSION=3.23 ARG ALPINE_VERSION=3.24
FROM alpine:${ALPINE_VERSION} FROM alpine:${ALPINE_VERSION}
ARG BUILDER_UID=1000 ARG BUILDER_UID=1000
@@ -18,9 +18,15 @@ RUN addgroup -g "${BUILDER_GID}" builder \
&& adduser -D -u "${BUILDER_UID}" -G builder builder \ && adduser -D -u "${BUILDER_UID}" -G builder builder \
&& addgroup builder abuild \ && addgroup builder abuild \
&& addgroup builder wheel \ && addgroup builder wheel \
&& mkdir -p /var/cache/distfiles /home/builder/packages \ && mkdir -p \
/var/cache/distfiles \
/home/builder/.cache/cargo \
/home/builder/.cache/cargo-target \
/home/builder/.cache/rustup \
/home/builder/packages \
&& chgrp abuild /var/cache/distfiles /home/builder/packages \ && chgrp abuild /var/cache/distfiles /home/builder/packages \
&& chmod g+w /var/cache/distfiles /home/builder/packages \ && chmod g+w /var/cache/distfiles /home/builder/packages \
&& chown -R builder:builder /home/builder/.cache \
&& printf 'permit nopass :wheel\n' > /etc/doas.d/wheel.conf \ && printf 'permit nopass :wheel\n' > /etc/doas.d/wheel.conf \
&& printf '%%wheel ALL=(ALL) NOPASSWD: ALL\n' > /etc/sudoers.d/wheel && printf '%%wheel ALL=(ALL) NOPASSWD: ALL\n' > /etc/sudoers.d/wheel
+71 -13
View File
@@ -6,7 +6,7 @@ requested_arch="${2:-${ALPINE_ARCH:-x86_64}}"
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
. "${repo_root}/scripts/apk/package-lib.sh" . "${repo_root}/scripts/apk/package-lib.sh"
alpine_version="${ALPINE_VERSION:-3.23}" alpine_version="${ALPINE_VERSION:-3.24}"
repo_name="${ALPINE_REPO_NAME:-local}" repo_name="${ALPINE_REPO_NAME:-local}"
build_platform="${ALPINE_BUILD_PLATFORM:-linux/amd64}" build_platform="${ALPINE_BUILD_PLATFORM:-linux/amd64}"
builder_uid="$(id -u)" builder_uid="$(id -u)"
@@ -19,6 +19,41 @@ if [[ "${builder_gid}" == "0" ]]; then
builder_gid=1000 builder_gid=1000
fi fi
image_name="${ALPINE_APK_BUILDER_IMAGE:-alpine-apk-builder:${alpine_version}-${builder_uid}-${builder_gid}}"
cache_scope_from_remote() {
local remote
local path
local owner
local repo
remote="$(git -C "${repo_root}" remote get-url origin 2>/dev/null || true)"
remote="${remote%.git}"
case "${remote}" in
ssh://*/*/*)
path="${remote#ssh://*/}"
;;
http://*/*/*|https://*/*/*)
path="${remote#*://*/}"
;;
*:*)
path="${remote#*:}"
;;
*)
path="$(basename "${repo_root}")"
;;
esac
owner="$(basename "$(dirname "${path}")")"
repo="$(basename "${path}")"
if [[ -n "${owner}" && "${owner}" != "." && -n "${repo}" ]]; then
printf '%s-%s\n' "${owner}" "${repo}" | sed 's/[^A-Za-z0-9_.-]/-/g'
else
printf '%s\n' "$(basename "${repo_root}")" | sed 's/[^A-Za-z0-9_.-]/-/g'
fi
}
validate_arch() { validate_arch() {
case "$1" in case "$1" in
x86_64|aarch64) ;; x86_64|aarch64) ;;
@@ -30,22 +65,17 @@ run_for_arch() {
local arch="$1" local arch="$1"
local subcommand="$2" local subcommand="$2"
local package_dir="$3" local package_dir="$3"
local image_name
local container_package_dir local container_package_dir
local package_name
local cache_scope
local cache_prefix
validate_arch "${arch}" validate_arch "${arch}"
apk_validate_package_dir "${package_dir}" apk_validate_package_dir "${package_dir}"
package_name="$(apk_package_name "${package_dir}")"
container_package_dir="$(apk_container_package_dir "${repo_root}" "${package_dir}")" container_package_dir="$(apk_container_package_dir "${repo_root}" "${package_dir}")"
image_name="${ALPINE_APK_BUILDER_IMAGE:-alpine-apk-builder:${arch}}" cache_scope="${ALPINE_APK_CACHE_SCOPE:-$(cache_scope_from_remote)}"
cache_prefix="${ALPINE_APK_CACHE_PREFIX:-alpine-apk}-${cache_scope}-${package_name}-${arch}"
docker build \
--platform "${build_platform}" \
--build-arg "ALPINE_VERSION=${alpine_version}" \
--build-arg "BUILDER_UID=${builder_uid}" \
--build-arg "BUILDER_GID=${builder_gid}" \
-f "${repo_root}/scripts/apk/Dockerfile" \
-t "${image_name}" \
"${repo_root}"
docker_args=(--rm --platform "${build_platform}") docker_args=(--rm --platform "${build_platform}")
if [[ -t 0 && -t 1 ]]; then if [[ -t 0 && -t 1 ]]; then
@@ -57,7 +87,13 @@ run_for_arch() {
-e "CARCH=${arch}" \ -e "CARCH=${arch}" \
-e "ALPINE_REPO_NAME=${repo_name}" \ -e "ALPINE_REPO_NAME=${repo_name}" \
-e "APKBUILD_DIR=${container_package_dir}" \ -e "APKBUILD_DIR=${container_package_dir}" \
-e "PACKAGER=${PACKAGER:-Joachim Schlöffel <me@joachim-schloeffel.com>}" \ -e "CARGO_HOME=/home/builder/.cache/cargo" \
-e "CARGO_TARGET_DIR=/home/builder/.cache/cargo-target" \
-e "PACKAGER=${PACKAGER:-local}" \
-e "RUSTUP_HOME=/home/builder/.cache/rustup" \
-v "${cache_prefix}-cargo:/home/builder/.cache/cargo" \
-v "${cache_prefix}-cargo-target:/home/builder/.cache/cargo-target" \
-v "${cache_prefix}-rustup:/home/builder/.cache/rustup" \
-v "${repo_root}:/work" \ -v "${repo_root}:/work" \
-v "${repo_root}/.cache/abuild:/home/builder/.abuild" \ -v "${repo_root}/.cache/abuild:/home/builder/.abuild" \
-v "${repo_root}/.cache/apk-distfiles:/var/cache/distfiles" \ -v "${repo_root}/.cache/apk-distfiles:/var/cache/distfiles" \
@@ -66,11 +102,33 @@ run_for_arch() {
"${subcommand}" "${subcommand}"
} }
build_builder_image() {
docker build \
--platform "${build_platform}" \
--build-arg "ALPINE_VERSION=${alpine_version}" \
--build-arg "BUILDER_UID=${builder_uid}" \
--build-arg "BUILDER_GID=${builder_gid}" \
-f "${repo_root}/scripts/apk/Dockerfile" \
-t "${image_name}" \
"${repo_root}"
}
mkdir -p \ mkdir -p \
"${repo_root}/.cache/abuild" \ "${repo_root}/.cache/abuild" \
"${repo_root}/.cache/apk-distfiles" \ "${repo_root}/.cache/apk-distfiles" \
"${repo_root}/packages" "${repo_root}/packages"
case "${command_name}" in
build-all|build|checksum|lint|shell) ;;
*)
printf 'unknown command: %s\n' "${command_name}" >&2
printf 'usage: %s [build|build-all|checksum|lint|shell] [x86_64|aarch64]\n' "$0" >&2
exit 2
;;
esac
build_builder_image
case "${command_name}" in case "${command_name}" in
build-all) build-all)
while IFS= read -r package_dir; do while IFS= read -r package_dir; do
+20 -4
View File
@@ -2,12 +2,19 @@
set -euo pipefail set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
# shellcheck source=scripts/apk/package-lib.sh
. "${repo_root}/scripts/apk/package-lib.sh" . "${repo_root}/scripts/apk/package-lib.sh"
repo_name="${ALPINE_REPO_NAME:-local}" repo_name="${ALPINE_REPO_NAME:-local}"
arches="${ALPINE_ARCHES:-x86_64 aarch64}" arches="${ALPINE_ARCHES:-x86_64 aarch64}"
packager="${PACKAGER:-Joachim Schlöffel <me@joachim-schloeffel.com>}" packager="${PACKAGER:-local}"
selected_packages="${ALPINE_PACKAGE:-${ALPINE_PACKAGES:-}}" selected_packages="${ALPINE_PACKAGE:-${ALPINE_PACKAGES:-}}"
skip_build="${ALPINE_SKIP_BUILD:-0}"
if [[ "${skip_build}" == "1" ]]; then
printf 'Skipping package build: restored package cache is complete\n'
exit 0
fi
if [[ "${1:-}" != "--as-builder" && "$(id -u)" == "0" ]]; then if [[ "${1:-}" != "--as-builder" && "$(id -u)" == "0" ]]; then
addgroup -g 1000 builder 2>/dev/null || addgroup builder addgroup -g 1000 builder 2>/dev/null || addgroup builder
@@ -24,6 +31,15 @@ export PACKAGER="${packager}"
export REPODEST="${repo_root}/packages" export REPODEST="${repo_root}/packages"
export SRCDEST="${repo_root}/.cache/apk-distfiles" export SRCDEST="${repo_root}/.cache/apk-distfiles"
install_repo_keys() {
local key
shopt -s nullglob
for key in "${REPODEST}/${repo_name}"/*/*.rsa.pub; do
doas cp "${key}" /etc/apk/keys/
done
shopt -u nullglob
}
git config --global --add safe.directory "${repo_root}" git config --global --add safe.directory "${repo_root}"
mkdir -p "${repo_root}/.cache/abuild" "${SRCDEST}" "${REPODEST}" "${HOME}/.abuild" mkdir -p "${repo_root}/.cache/abuild" "${SRCDEST}" "${REPODEST}" "${HOME}/.abuild"
@@ -37,6 +53,8 @@ if ! compgen -G "${HOME}/.abuild/*.rsa" > /dev/null; then
fi fi
doas cp "${HOME}"/.abuild/*.rsa.pub /etc/apk/keys/ doas cp "${HOME}"/.abuild/*.rsa.pub /etc/apk/keys/
install_repo_keys
doas apk update
while IFS= read -r package_dir; do while IFS= read -r package_dir; do
apk_validate_package_dir "${package_dir}" apk_validate_package_dir "${package_dir}"
@@ -54,10 +72,8 @@ while IFS= read -r package_dir; do
printf 'Building %s for %s\n' "$(basename "${package_dir}")" "${arch}" printf 'Building %s for %s\n' "$(basename "${package_dir}")" "${arch}"
( (
export ALPINE_ARCH="${arch}"
export CARCH="${arch}"
cd "${package_dir}" cd "${package_dir}"
abuild -r ALPINE_ARCH="${arch}" CARCH="${arch}" abuild -r
) )
mkdir -p "${REPODEST}/${repo_name}/${arch}" mkdir -p "${REPODEST}/${repo_name}/${arch}"
+249
View File
@@ -0,0 +1,249 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
# shellcheck source=scripts/apk/package-lib.sh
. "${repo_root}/scripts/apk/package-lib.sh"
repo_name="${ALPINE_REPO_NAME:-local}"
arches="${ALPINE_ARCHES:-x86_64 aarch64}"
cache_root="${ALPINE_APK_REPO_CACHE:-/cache/public-alpine-packages/${ALPINE_REGISTRY_BRANCH:-local}/apk-repo}"
repo_dest="${repo_root}/packages/${repo_name}"
command_name="${1:-prepare}"
all_packages() {
while IFS= read -r package_dir; do
apk_package_name "${package_dir}"
done < <(apk_all_package_dirs "${repo_root}")
}
mark_all_packages() {
local reason="$1"
printf 'Rebuilding all packages: %s\n' "${reason}" >&2
all_packages
}
diff_base() {
local before="${GITHUB_EVENT_BEFORE:-${CI_COMMIT_BEFORE_SHA:-}}"
local base_ref="${GITHUB_BASE_REF:-}"
if [[ -n "${base_ref}" ]] && git rev-parse --verify "origin/${base_ref}" >/dev/null 2>&1; then
printf '%s...HEAD\n' "origin/${base_ref}"
return
fi
if [[ -n "${before}" && ! "${before}" =~ ^0+$ ]] && git rev-parse --verify "${before}^{commit}" >/dev/null 2>&1; then
printf '%s..HEAD\n' "${before}"
return
fi
if git rev-parse --verify "HEAD^" >/dev/null 2>&1; then
printf 'HEAD^..HEAD\n'
return
fi
return 1
}
changed_packages() {
local base
local changed_paths
local changed_path
local package
declare -A selected=()
if ! base="$(diff_base)"; then
mark_all_packages "no usable git diff base"
return
fi
if ! changed_paths="$(git diff --name-only "${base}")"; then
mark_all_packages "git diff failed for ${base}"
return
fi
while IFS= read -r changed_path; do
[[ -n "${changed_path}" ]] || continue
case "${changed_path}" in
scripts/apk/*|.gitea/workflows/build.yml|mise.toml)
mark_all_packages "shared build logic changed"
return
;;
packaging/alpine/local/*)
package="${changed_path#packaging/alpine/local/}"
package="${package%%/*}"
selected["${package}"]=1
;;
esac
done <<< "${changed_paths}"
for package in "${!selected[@]}"; do
printf '%s\n' "${package}"
done | sort
}
restore_cache() {
if [[ -d "${cache_root}" ]]; then
mkdir -p "${repo_dest}"
cp -a "${cache_root}/." "${repo_dest}/"
printf 'Restored Alpine package repository cache from %s\n' "${cache_root}"
else
printf 'No Alpine package repository cache found at %s\n' "${cache_root}"
fi
}
package_apk_names() {
local package_dir="$1"
local arch="$2"
apk_package_apk_names "${package_dir}" "${arch}"
}
package_cache_complete() {
local package_dir="$1"
local package_name
local arch
local apk_name
package_name="$(apk_package_name "${package_dir}")"
for arch in ${arches}; do
case "${arch}" in
x86_64|aarch64) ;;
*) printf 'unsupported Alpine architecture: %s\n' "${arch}" >&2; exit 2 ;;
esac
if ! apk_package_supports_arch "${package_dir}" "${arch}"; then
continue
fi
while IFS= read -r apk_name; do
if [[ ! -f "${repo_dest}/${arch}/${apk_name}" ]]; then
printf 'Cache miss for %s: missing %s/%s\n' "${package_name}" "${arch}" "${apk_name}" >&2
return 1
fi
done < <(package_apk_names "${package_dir}" "${arch}")
done
return 0
}
select_missing_packages() {
local package_dir
local package_name
while IFS= read -r package_dir; do
apk_validate_package_dir "${package_dir}"
package_name="$(apk_package_name "${package_dir}")"
if ! package_cache_complete "${package_dir}"; then
printf '%s\n' "${package_name}"
fi
done < <(apk_all_package_dirs "${repo_root}")
}
prune_stale_apks() {
local package_dir
local arch
local apk_name
local current_apk
declare -A expected_apks=()
if [[ ! -d "${repo_dest}" ]]; then
return
fi
while IFS= read -r package_dir; do
apk_validate_package_dir "${package_dir}"
for arch in ${arches}; do
case "${arch}" in
x86_64|aarch64) ;;
*) printf 'unsupported Alpine architecture: %s\n' "${arch}" >&2; exit 2 ;;
esac
if ! apk_package_supports_arch "${package_dir}" "${arch}"; then
continue
fi
while IFS= read -r apk_name; do
expected_apks["${repo_dest}/${arch}/${apk_name}"]=1
done < <(package_apk_names "${package_dir}" "${arch}")
done
done < <(apk_all_package_dirs "${repo_root}")
shopt -s nullglob
for current_apk in "${repo_dest}"/*/*.apk; do
if [[ -z "${expected_apks[${current_apk}]:-}" ]]; then
rm -f "${current_apk}"
printf 'Pruned stale cached APK: %s\n' "${current_apk#"${repo_root}/"}"
fi
done
shopt -u nullglob
}
prepare() {
local selected_packages
local selected
declare -A selected_map=()
restore_cache
prune_stale_apks
while IFS= read -r selected; do
[[ -n "${selected}" ]] || continue
selected_map["${selected}"]=1
done < <(changed_packages)
while IFS= read -r selected; do
[[ -n "${selected}" ]] || continue
selected_map["${selected}"]=1
done < <(select_missing_packages)
selected_packages="$(
for selected in "${!selected_map[@]}"; do
printf '%s\n' "${selected}"
done | sort | xargs
)"
if [[ -n "${selected_packages}" ]]; then
printf 'Selected packages for rebuild: %s\n' "${selected_packages}"
export ALPINE_PACKAGES="${selected_packages}"
export ALPINE_SKIP_BUILD=0
else
printf 'No packages selected for rebuild\n'
export ALPINE_PACKAGES=""
export ALPINE_SKIP_BUILD=1
fi
if [[ -n "${GITHUB_ENV:-}" ]]; then
{
printf 'ALPINE_PACKAGES=%s\n' "${ALPINE_PACKAGES}"
printf 'ALPINE_SKIP_BUILD=%s\n' "${ALPINE_SKIP_BUILD}"
} >> "${GITHUB_ENV}"
fi
}
sync_cache() {
if [[ ! -d "${repo_dest}" ]]; then
printf 'missing package repository: %s\n' "${repo_dest}" >&2
exit 1
fi
prune_stale_apks
mkdir -p "${cache_root}"
rsync -a --delete "${repo_dest}/" "${cache_root}/"
printf 'Updated Alpine package repository cache at %s\n' "${cache_root}"
}
case "${command_name}" in
prepare)
prepare
;;
sync)
sync_cache
;;
*)
printf 'usage: %s [prepare|sync]\n' "$0" >&2
exit 2
;;
esac
+21 -3
View File
@@ -4,7 +4,7 @@ set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
repo_name="${ALPINE_REPO_NAME:-local}" repo_name="${ALPINE_REPO_NAME:-local}"
arch="${ALPINE_ARCH:-$(apk --print-arch)}" arch="${ALPINE_ARCH:-$(apk --print-arch)}"
packages="${SMOKE_PACKAGES:-seaweedfs seaweedfs-master-openrc seaweedfs-filer-openrc seaweedfs-worker-openrc greptimedb}" packages="${SMOKE_PACKAGES:-seaweedfs seaweedfs-master-openrc seaweedfs-filer-openrc seaweedfs-worker-openrc greptimedb lavinmq lavinmq-openrc gitea gitea-openrc}"
repo_dir="${repo_root}/packages/${repo_name}/${arch}" repo_dir="${repo_root}/packages/${repo_name}/${arch}"
read -r -a package_list <<< "${packages}" read -r -a package_list <<< "${packages}"
@@ -17,11 +17,29 @@ cp "${repo_dir}"/*.rsa.pub /etc/apk/keys/
echo "${repo_root}/packages/${repo_name}" >> /etc/apk/repositories echo "${repo_root}/packages/${repo_name}" >> /etc/apk/repositories
apk update apk update
apk add "${package_list[@]}" apk add "${package_list[@]}"
weed version if command -v weed >/dev/null 2>&1; then
weed version
ls -1 /etc/seaweedfs
fi
if command -v greptime >/dev/null 2>&1; then if command -v greptime >/dev/null 2>&1; then
greptime --version greptime --version
fi fi
ls -1 /etc/seaweedfs if command -v lavinmq >/dev/null 2>&1; then
lavinmq -v
lavinmqctl --version
lavinmqperf --version
fi
if command -v gitea >/dev/null 2>&1; then
gitea --version
test -f /etc/gitea/app.ini
test -d /var/lib/gitea
fi
if ls /etc/init.d/seaweedfs.* >/dev/null 2>&1; then if ls /etc/init.d/seaweedfs.* >/dev/null 2>&1; then
find /etc/init.d -maxdepth 1 -name 'seaweedfs.*' -print | sort find /etc/init.d -maxdepth 1 -name 'seaweedfs.*' -print | sort
fi fi
if [[ -f /etc/init.d/lavinmq ]]; then
printf '%s\n' /etc/init.d/lavinmq
fi
if [[ -f /etc/init.d/gitea ]]; then
printf '%s\n' /etc/init.d/gitea
fi
+12 -1
View File
@@ -7,7 +7,7 @@ repo_name="${ALPINE_REPO_NAME:-local}"
arch="${ALPINE_ARCH:-x86_64}" arch="${ALPINE_ARCH:-x86_64}"
export CARCH="${CARCH:-$arch}" export CARCH="${CARCH:-$arch}"
export PACKAGER="${PACKAGER:-Joachim Schlöffel <me@joachim-schloeffel.com>}" export PACKAGER="${PACKAGER:-local}"
if [[ -n "${PACKAGER_PRIVKEY:-}" ]]; then if [[ -n "${PACKAGER_PRIVKEY:-}" ]]; then
export PACKAGER_PRIVKEY export PACKAGER_PRIVKEY
fi fi
@@ -15,6 +15,15 @@ fi
git config --global --add safe.directory /work git config --global --add safe.directory /work
mkdir -p /home/builder/.abuild /home/builder/packages "${package_dir}" mkdir -p /home/builder/.abuild /home/builder/packages "${package_dir}"
install_repo_keys() {
local key
shopt -s nullglob
for key in "/home/builder/packages/${repo_name}"/*/*.rsa.pub; do
doas cp "${key}" /etc/apk/keys/
done
shopt -u nullglob
}
if [[ -n "${PACKAGER_PRIVKEY:-}" && ! -f "${PACKAGER_PRIVKEY}" ]]; then if [[ -n "${PACKAGER_PRIVKEY:-}" && ! -f "${PACKAGER_PRIVKEY}" ]]; then
abuild-keygen -a -n abuild-keygen -a -n
elif ! compgen -G "/home/builder/.abuild/*.rsa" > /dev/null; then elif ! compgen -G "/home/builder/.abuild/*.rsa" > /dev/null; then
@@ -34,9 +43,11 @@ if [[ -n "${PACKAGER_PRIVKEY:-}" && -f "${PACKAGER_PRIVKEY}.pub" ]]; then
elif compgen -G "/home/builder/.abuild/*.rsa.pub" > /dev/null; then elif compgen -G "/home/builder/.abuild/*.rsa.pub" > /dev/null; then
doas cp /home/builder/.abuild/*.rsa.pub /etc/apk/keys/ doas cp /home/builder/.abuild/*.rsa.pub /etc/apk/keys/
fi fi
install_repo_keys
case "${command_name}" in case "${command_name}" in
build) build)
doas apk update
cd "${package_dir}" cd "${package_dir}"
abuild -r abuild -r
mkdir -p "/home/builder/packages/${repo_name}/${arch}" mkdir -p "/home/builder/packages/${repo_name}/${arch}"
+39
View File
@@ -0,0 +1,39 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
repo_name="${ALPINE_REPO_NAME:-local}"
package_name="${ALPINE_PACKAGE:-greptimedb}"
package_root="${repo_root}/packages/${repo_name}"
assets_dir="${CI_ASSETS_DIR:-${repo_root}/packages/ci-assets}"
if [[ ! -d "${package_root}" ]]; then
printf 'missing local package repository: %s\n' "${package_root}" >&2
exit 1
fi
mkdir -p "${assets_dir}"
shopt -s nullglob
apks=("${package_root}"/*/"${package_name}"-[0-9]*.apk)
shopt -u nullglob
if [[ "${#apks[@]}" -eq 0 ]]; then
printf 'no %s APK files found under %s\n' "${package_name}" "${package_root}" >&2
exit 1
fi
for apk in "${apks[@]}"; do
arch="$(basename "$(dirname "${apk}")")"
pkgver="$(
tar -xOf "${apk}" .PKGINFO 2>/dev/null \
| awk -F' = ' '$1 == "pkgver" { print $2; exit }'
)"
version="${pkgver%-r*}"
asset="${assets_dir}/greptime-linux-${arch}-musl-v${version}"
printf 'Exporting %s\n' "${asset}"
tar -xOf "${apk}" usr/bin/greptime > "${asset}"
chmod 0755 "${asset}"
sha256sum "${asset}" > "${asset}.sha256sum"
done
+8
View File
@@ -0,0 +1,8 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
shellcheck \
"${repo_root}"/scripts/apk/*.sh \
"${repo_root}"/packaging/alpine/local/*/scripts/*.sh
+22
View File
@@ -2,7 +2,25 @@
set -euo pipefail set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
# shellcheck source=scripts/apk/package-lib.sh
. "${repo_root}/scripts/apk/package-lib.sh"
repo_dir="${repo_root}/packages/local" repo_dir="${repo_root}/packages/local"
arches="${ALPINE_ARCHES:-x86_64 aarch64}"
declare -A expected_apks=()
while IFS= read -r package_source_dir; do
apk_validate_package_dir "${package_source_dir}"
for arch in ${arches}; do
if ! apk_package_supports_arch "${package_source_dir}" "${arch}"; then
continue
fi
while IFS= read -r apk_name; do
expected_apks["${repo_dir}/${arch}/${apk_name}"]=1
done < <(apk_package_apk_names "${package_source_dir}" "${arch}")
done
done < <(apk_all_package_dirs "${repo_root}")
if [[ -n "${ALPINE_ARCH:-}" ]]; then if [[ -n "${ALPINE_ARCH:-}" ]]; then
package_dirs=("${repo_dir}/${ALPINE_ARCH}") package_dirs=("${repo_dir}/${ALPINE_ARCH}")
@@ -29,6 +47,10 @@ for package_dir in "${package_dirs[@]}"; do
printf '## %s\n' "$(basename "${package_dir}")" printf '## %s\n' "$(basename "${package_dir}")"
for apk in "${apks[@]}"; do for apk in "${apks[@]}"; do
if [[ -z "${expected_apks[${apk}]:-}" ]]; then
printf 'Skipping stale local APK: %s\n' "${apk#"${repo_root}/"}"
continue
fi
printf '### %s\n' "$(basename "${apk}")" printf '### %s\n' "$(basename "${apk}")"
tar -xOf "${apk}" .PKGINFO 2>/dev/null \ tar -xOf "${apk}" .PKGINFO 2>/dev/null \
| sed -n '/^pkgname =/p;/^pkgver =/p;/^arch =/p;/^depend =/p;/^provides =/p;/^install_if =/p' | sed -n '/^pkgname =/p;/^pkgver =/p;/^arch =/p;/^depend =/p;/^provides =/p;/^install_if =/p'
+144
View File
@@ -0,0 +1,144 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
# shellcheck source=scripts/apk/package-lib.sh
source "${repo_root}/scripts/apk/package-lib.sh"
mode="${APK_UPDATE_CHECK_MODE:-warn}"
if [[ "${mode}" != "warn" && "${mode}" != "fail" ]]; then
printf 'APK_UPDATE_CHECK_MODE must be warn or fail\n' >&2
exit 2
fi
github_latest_release() {
local repo="$1"
local api_url="https://api.github.com/repos/${repo}/releases/latest"
local response
response="$(curl -fsSL \
-H 'Accept: application/vnd.github+json' \
-H 'X-GitHub-Api-Version: 2022-11-28' \
"${api_url}" 2>/dev/null)" || return 1
printf '%s\n' "${response}" \
| sed -n 's/^[[:space:]]*"tag_name":[[:space:]]*"\([^"]*\)".*/\1/p' \
| head -n 1
}
apkbuild_value() {
local package_dir="$1"
local key="$2"
awk -F= -v key="${key}" '
$1 == key {
value = $2
gsub(/["'\'']/, "", value)
gsub(/^[ \t]+|[ \t]+$/, "", value)
print value
exit
}
' "${package_dir}/APKBUILD"
}
load_update_metadata() {
local package_dir="$1"
local metadata="${package_dir}/update-check.conf"
provider=""
repo=""
version_prefix="v"
if [[ ! -f "${metadata}" ]]; then
return 1
fi
# shellcheck source=/dev/null
source "${metadata}"
if [[ "${provider}" != "github" || -z "${repo}" ]]; then
return 1
fi
}
normalize_version() {
local version="$1"
local prefix="$2"
case "${prefix}" in
none|"")
printf '%s\n' "${version}"
;;
*)
printf '%s\n' "${version#"${prefix}"}"
;;
esac
}
version_is_newer() {
local latest="$1"
local current="$2"
local apk_result
local sorted
if [[ "${latest}" == "${current}" ]]; then
return 1
fi
if command -v apk >/dev/null 2>&1; then
apk_result="$(apk version -t "${latest}-r0" "${current}-r0" 2>/dev/null || true)"
[[ "${apk_result}" == ">" ]]
return
fi
if sort -V </dev/null >/dev/null 2>&1; then
sorted="$(printf '%s\n%s\n' "${current}" "${latest}" | sort -V | tail -n 1)"
[[ "${sorted}" == "${latest}" && "${latest}" != "${current}" ]]
return
fi
return 0
}
printf '%-14s %-14s %-14s %-18s %s\n' "PACKAGE" "CURRENT" "LATEST" "STATUS" "UPSTREAM"
has_update=0
has_unknown=0
while IFS= read -r package_dir; do
apk_validate_package_dir "${package_dir}"
package_name="$(apk_package_name "${package_dir}")"
current_version="$(apkbuild_value "${package_dir}" "pkgver")"
status="unknown"
latest_version="-"
upstream_url="-"
if load_update_metadata "${package_dir}"; then
upstream_url="https://github.com/${repo}/releases"
if latest_tag="$(github_latest_release "${repo}")" && [[ -n "${latest_tag}" ]]; then
latest_version="$(normalize_version "${latest_tag}" "${version_prefix}")"
if version_is_newer "${latest_version}" "${current_version}"; then
status="update-available"
has_update=1
else
status="current"
fi
else
has_unknown=1
fi
else
has_unknown=1
fi
printf '%-14s %-14s %-14s %-18s %s\n' \
"${package_name}" \
"${current_version:-"-"}" \
"${latest_version}" \
"${status}" \
"${upstream_url}"
done < <(apk_package_dirs "${repo_root}")
if [[ "${mode}" == "fail" && ( "${has_update}" -ne 0 || "${has_unknown}" -ne 0 ) ]]; then
exit 1
fi
+32
View File
@@ -37,6 +37,14 @@ apk_package_dirs() {
return return
fi fi
apk_all_package_dirs "${repo_root}"
}
apk_all_package_dirs() {
local repo_root="$1"
local package_root
package_root="$(apk_package_root "${repo_root}")"
find "${package_root}" -mindepth 2 -maxdepth 2 -name APKBUILD -print \ find "${package_root}" -mindepth 2 -maxdepth 2 -name APKBUILD -print \
| sed 's#/APKBUILD$##' \ | sed 's#/APKBUILD$##' \
| sort | sort
@@ -87,6 +95,30 @@ apk_package_supports_arch() {
return 1 return 1
} }
apk_package_apk_names() {
local package_dir="$1"
local arch="$2"
(
set +u
local pkgname
local pkgver
local pkgrel
local subpackage
local subpackages
export CARCH="${arch}"
cd "${package_dir}" || exit 1
# shellcheck source=/dev/null
. ./APKBUILD
printf '%s-%s-r%s.apk\n' "${pkgname}" "${pkgver}" "${pkgrel}"
for subpackage in ${subpackages:-}; do
subpackage="${subpackage%%:*}"
printf '%s-%s-r%s.apk\n' "${subpackage}" "${pkgver}" "${pkgrel}"
done
)
}
apk_container_package_dir() { apk_container_package_dir() {
local repo_root="$1" local repo_root="$1"
local package_dir="$2" local package_dir="$2"
+2
View File
@@ -4,7 +4,9 @@ set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
cd "${repo_root}" cd "${repo_root}"
mise run apk:outdated
mise run apk:lint mise run apk:lint
mise run apk:lint-shell
mise run apk:build-all mise run apk:build-all
mise run apk:packages mise run apk:packages
mise run apk:smoke mise run apk:smoke
+39 -2
View File
@@ -2,8 +2,12 @@
set -euo pipefail set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
# shellcheck source=scripts/apk/package-lib.sh
. "${repo_root}/scripts/apk/package-lib.sh"
repo_name="${ALPINE_REPO_NAME:-local}" repo_name="${ALPINE_REPO_NAME:-local}"
alpine_version="${ALPINE_VERSION:-3.23}" alpine_version="${ALPINE_VERSION:-3.24}"
arches="${ALPINE_ARCHES:-x86_64 aarch64}"
branch="${ALPINE_REGISTRY_BRANCH:-v${alpine_version}}" branch="${ALPINE_REGISTRY_BRANCH:-v${alpine_version}}"
repository="${ALPINE_REGISTRY_REPOSITORY:-${PACKAGE_NAME:-main}}" repository="${ALPINE_REGISTRY_REPOSITORY:-${PACKAGE_NAME:-main}}"
instance_url="${INSTANCE_URL:-}" instance_url="${INSTANCE_URL:-}"
@@ -46,9 +50,42 @@ if [[ "${#apks[@]}" -eq 0 ]]; then
exit 1 exit 1
fi fi
printf 'Publishing %d APK files to %s\n' "${#apks[@]}" "${upload_url}" declare -A expected_apks=()
while IFS= read -r package_dir; do
apk_validate_package_dir "${package_dir}"
for arch in ${arches}; do
if ! apk_package_supports_arch "${package_dir}" "${arch}"; then
continue
fi
while IFS= read -r apk_name; do
expected_apks["${package_root}/${arch}/${apk_name}"]=1
done < <(apk_package_apk_names "${package_dir}" "${arch}")
done
done < <(apk_all_package_dirs "${repo_root}")
current_apks=()
stale_count=0
for apk in "${apks[@]}"; do for apk in "${apks[@]}"; do
if [[ -z "${expected_apks[${apk}]:-}" ]]; then
printf 'Skipping stale local APK: %s\n' "${apk#"${repo_root}/"}"
stale_count=$((stale_count + 1))
continue
fi
current_apks+=("${apk}")
done
if [[ "${#current_apks[@]}" -eq 0 ]]; then
printf 'no current APK files found under %s\n' "${package_root}" >&2
exit 1
fi
printf 'Publishing %d APK files to %s\n' "${#current_apks[@]}" "${upload_url}"
if [[ "${stale_count}" -ne 0 ]]; then
printf 'Skipping %d stale local APK file(s)\n' "${stale_count}"
fi
for apk in "${current_apks[@]}"; do
filename="$(basename "${apk}")" filename="$(basename "${apk}")"
status="$( status="$(
curl --silent --show-error --location \ curl --silent --show-error --location \
+4
View File
@@ -0,0 +1,4 @@
ARG ALPINE_VERSION=3.24
FROM alpine:${ALPINE_VERSION}
RUN apk add --no-cache bash openrc
+149
View File
@@ -0,0 +1,149 @@
#!/usr/bin/env bash
set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
. "${repo_root}/scripts/apk/package-lib.sh"
alpine_version="${ALPINE_VERSION:-3.24}"
repo_name="${ALPINE_REPO_NAME:-local}"
arch="${ALPINE_ARCH:-x86_64}"
platform="${ALPINE_TEST_PLATFORM:-linux/amd64}"
repo_dir="${repo_root}/packages/${repo_name}/${arch}"
runtime_mode="${ALPINE_RUNTIME_TEST_MODE:-auto}"
runtime_image="${ALPINE_RUNTIME_TEST_IMAGE:-alpine-apk-runtime-test:${alpine_version}}"
validate_repo() {
if [[ ! -d "${repo_dir}" ]]; then
printf 'missing local repository: packages/%s/%s\n' "${repo_name}" "${arch}" >&2
printf 'run: ALPINE_ARCH=%s mise run apk:build\n' "${arch}" >&2
exit 1
fi
shopt -s nullglob
repo_keys=("${repo_dir}"/*.rsa.pub)
repo_indexes=("${repo_dir}"/APKINDEX.tar.gz)
shopt -u nullglob
if [[ "${#repo_keys[@]}" -eq 0 ]]; then
printf 'missing repository key: packages/%s/%s/*.rsa.pub\n' "${repo_name}" "${arch}" >&2
exit 1
fi
if [[ "${#repo_indexes[@]}" -eq 0 ]]; then
printf 'missing repository index: packages/%s/%s/APKINDEX.tar.gz\n' "${repo_name}" "${arch}" >&2
exit 1
fi
}
in_alpine() {
[[ -f /etc/alpine-release ]] && command -v apk >/dev/null 2>&1
}
prepare_direct_runtime() {
apk add --no-cache bash openrc >/dev/null
cp "${repo_dir}"/*.rsa.pub /etc/apk/keys/
printf '%s\n' "${repo_root}/packages/${repo_name}" >> /etc/apk/repositories
apk update
mkdir -p /run/openrc
touch /run/openrc/softlevel
}
run_hook_direct() {
local hook_path="$1"
local package_dir="$2"
local package_name="$3"
PACKAGE_DIR="${package_dir}" \
PACKAGE_NAME="${package_name}" \
"${hook_path}"
}
run_hook_docker() {
local package_dir_rel="$1"
docker run --rm --privileged --platform "${platform}" \
-e "ALPINE_ARCH=${arch}" \
-e "ALPINE_REPO_NAME=${repo_name}" \
-e "PACKAGE_DIR=/work/${package_dir_rel}" \
-e "PACKAGE_NAME=${package_name}" \
-v "${repo_root}:/work:ro" \
-v "${repo_root}/packages/${repo_name}:/repo:ro" \
"${runtime_image}" \
sh -lc '
set -e
cp "/repo/${ALPINE_ARCH}"/*.rsa.pub /etc/apk/keys/
printf "%s\n" /repo >> /etc/apk/repositories
apk update
mkdir -p /run/openrc
touch /run/openrc/softlevel
exec /bin/bash "${PACKAGE_DIR}/scripts/runtime-test.sh"
'
}
build_runtime_image() {
docker build \
--platform "${platform}" \
--build-arg "ALPINE_VERSION=${alpine_version}" \
-f "${repo_root}/scripts/apk/runtime-test.Dockerfile" \
-t "${runtime_image}" \
"${repo_root}"
}
validate_repo
case "${runtime_mode}" in
auto)
if in_alpine; then
runtime_mode="direct"
else
runtime_mode="docker"
fi
;;
direct|docker) ;;
*)
printf 'unsupported ALPINE_RUNTIME_TEST_MODE: %s\n' "${runtime_mode}" >&2
printf 'expected: auto, direct, or docker\n' >&2
exit 2
;;
esac
if [[ "${runtime_mode}" == "direct" ]]; then
prepare_direct_runtime
else
build_runtime_image
fi
while IFS= read -r package_dir; do
apk_validate_package_dir "${package_dir}"
package_name="$(apk_package_name "${package_dir}")"
hook_path="${package_dir}/scripts/runtime-test.sh"
if [[ ! -e "${hook_path}" ]]; then
printf 'Skipping %s: no runtime-test hook\n' "${package_name}"
continue
fi
if [[ ! -x "${hook_path}" ]]; then
printf 'package hook is not executable: %s\n' "${hook_path}" >&2
exit 1
fi
if ! apk_package_supports_arch "${package_dir}" "${arch}"; then
printf 'Skipping %s: unsupported arch %s\n' "${package_name}" "${arch}"
continue
fi
case "${package_dir}" in
"${repo_root}"/*)
package_dir_rel="${package_dir#"${repo_root}/"}"
;;
*)
printf 'package directory must be inside repository: %s\n' "${package_dir}" >&2
exit 1
;;
esac
printf 'Running runtime-test hook for %s\n' "${package_name}"
if [[ "${runtime_mode}" == "direct" ]]; then
run_hook_direct "${hook_path}" "${package_dir}" "${package_name}"
else
run_hook_docker "${package_dir_rel}"
fi
done < <(apk_package_dirs "${repo_root}")
+25 -4
View File
@@ -2,10 +2,10 @@
set -euo pipefail set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
alpine_version="${ALPINE_VERSION:-3.23}" alpine_version="${ALPINE_VERSION:-3.24}"
platform="${ALPINE_BUILD_PLATFORM:-linux/amd64}" platform="${ALPINE_BUILD_PLATFORM:-linux/amd64}"
arch="${ALPINE_ARCH:-x86_64}" arch="${ALPINE_ARCH:-x86_64}"
packages="${SMOKE_PACKAGES:-seaweedfs seaweedfs-master-openrc seaweedfs-filer-openrc seaweedfs-worker-openrc}" packages="${SMOKE_PACKAGES:-seaweedfs seaweedfs-master-openrc seaweedfs-filer-openrc seaweedfs-worker-openrc greptimedb lavinmq lavinmq-openrc gitea gitea-openrc}"
if [[ ! -d "${repo_root}/packages/local/${arch}" ]]; then if [[ ! -d "${repo_root}/packages/local/${arch}" ]]; then
printf 'missing local repository: packages/local/%s\n' "${arch}" >&2 printf 'missing local repository: packages/local/%s\n' "${arch}" >&2
@@ -22,9 +22,30 @@ docker run --rm --platform "${platform}" \
echo /repo >> /etc/apk/repositories echo /repo >> /etc/apk/repositories
apk update >/dev/null apk update >/dev/null
apk add ${packages} >/dev/null apk add ${packages} >/dev/null
weed version if command -v weed >/dev/null 2>&1; then
ls -1 /etc/seaweedfs weed version
ls -1 /etc/seaweedfs
fi
if command -v greptime >/dev/null 2>&1; then
greptime --version
fi
if command -v lavinmq >/dev/null 2>&1; then
lavinmq -v
lavinmqctl --version
lavinmqperf --version
fi
if command -v gitea >/dev/null 2>&1; then
gitea --version
test -f /etc/gitea/app.ini
test -d /var/lib/gitea
fi
if ls /etc/init.d/seaweedfs.* >/dev/null 2>&1; then if ls /etc/init.d/seaweedfs.* >/dev/null 2>&1; then
ls -1 /etc/init.d/seaweedfs.* | sort ls -1 /etc/init.d/seaweedfs.* | sort
fi fi
if [ -f /etc/init.d/lavinmq ]; then
ls -1 /etc/init.d/lavinmq
fi
if [ -f /etc/init.d/gitea ]; then
ls -1 /etc/init.d/gitea
fi
" "
+43
View File
@@ -0,0 +1,43 @@
#!/usr/bin/env bash
apk_test_install_run() {
local repo_root="$1"
local package_name="$2"
local package_version="$3"
local alpine_version="${ALPINE_VERSION:-3.24}"
local arch="${ALPINE_ARCH:-x86_64}"
local repository_url="${ALPINE_REPOSITORY_URL:-}"
local repository_key_url="${ALPINE_REPOSITORY_KEY_URL:-}"
local platform
local test_command
case "${arch}" in
x86_64) platform="${ALPINE_TEST_PLATFORM:-linux/amd64}" ;;
aarch64) platform="${ALPINE_TEST_PLATFORM:-linux/arm64}" ;;
*)
printf 'unsupported Alpine architecture: %s\n' "${arch}" >&2
return 2
;;
esac
if [[ -z "${repository_url}" && "${SKIP_BUILD:-0}" != "1" ]]; then
ALPINE_PACKAGE="${package_name}" "${repo_root}/scripts/apk/build.sh" build "${arch}"
fi
if [[ -z "${repository_url}" && ! -d "${repo_root}/packages/local/${arch}" ]]; then
printf 'missing local repository: packages/local/%s\n' "${arch}" >&2
printf 'run: ALPINE_PACKAGE=%s mise run apk:build\n' "${package_name}" >&2
return 1
fi
test_command="$(cat)"
docker run --rm --platform "${platform}" \
-e "ALPINE_ARCH=${arch}" \
-e "PACKAGE_NAME=${package_name}" \
-e "PACKAGE_VERSION=${package_version}" \
-e "ALPINE_REPOSITORY_URL=${repository_url}" \
-e "ALPINE_REPOSITORY_KEY_URL=${repository_key_url}" \
-v "${repo_root}/packages/local:/repo:ro" \
"alpine:${alpine_version}" \
sh -lc "${test_command}"
}
+38 -14
View File
@@ -2,11 +2,11 @@
set -euo pipefail set -euo pipefail
repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
alpine_version="${ALPINE_VERSION:-3.23}" alpine_version="${ALPINE_VERSION:-3.24}"
platform="${ALPINE_BUILD_PLATFORM:-linux/amd64}" platform="${ALPINE_BUILD_PLATFORM:-linux/amd64}"
arch="${ALPINE_ARCH:-x86_64}" arch="${ALPINE_ARCH:-x86_64}"
packages="${TEST_SHELL_PACKAGES:-seaweedfs seaweedfs-doc bash-completion seaweedfs-master-openrc seaweedfs-filer-openrc seaweedfs-worker-openrc}" packages="${TEST_SHELL_PACKAGES:-}"
shell="${TEST_SHELL:-/bin/bash}" shell="${TEST_SHELL:-/bin/sh}"
timeout_seconds="${TEST_SHELL_TIMEOUT:-120}" timeout_seconds="${TEST_SHELL_TIMEOUT:-120}"
case "${arch}" in case "${arch}" in
@@ -24,9 +24,23 @@ if [[ ! -d "${repo_root}/packages/local/${arch}" ]]; then
exit 1 exit 1
fi fi
docker_args=(--rm --platform "${platform}") shopt -s nullglob
repo_keys=("${repo_root}/packages/local/${arch}"/*.rsa.pub)
repo_indexes=("${repo_root}/packages/local/${arch}"/APKINDEX.tar.gz)
shopt -u nullglob
if [[ "${#repo_keys[@]}" -eq 0 ]]; then
printf 'missing repository key: packages/local/%s/*.rsa.pub\n' "${arch}" >&2
exit 1
fi
if [[ "${#repo_indexes[@]}" -eq 0 ]]; then
printf 'missing repository index: packages/local/%s/APKINDEX.tar.gz\n' "${arch}" >&2
exit 1
fi
docker_args=(--rm -i --platform "${platform}")
if [[ -t 0 && -t 1 ]]; then if [[ -t 0 && -t 1 ]]; then
docker_args+=(-it) docker_args+=(-t)
fi fi
docker run "${docker_args[@]}" \ docker run "${docker_args[@]}" \
@@ -46,15 +60,25 @@ docker run "${docker_args[@]}" \
printf "Refreshing apk indexes...\n" printf "Refreshing apk indexes...\n"
timeout "${TEST_SHELL_TIMEOUT}" apk update timeout "${TEST_SHELL_TIMEOUT}" apk update
printf "Installing test packages: %s\n" "${PACKAGE_LIST}" if [ -n "${PACKAGE_LIST}" ]; then
timeout "${TEST_SHELL_TIMEOUT}" apk add ${PACKAGE_LIST} printf "Installing requested test packages: %s\n" "${PACKAGE_LIST}"
timeout "${TEST_SHELL_TIMEOUT}" apk add ${PACKAGE_LIST}
fi
printf "\nInstalled SeaweedFS packages:\n" cat <<EOF
apk info -e seaweedfs seaweedfs-doc seaweedfs-bash-completion \
seaweedfs-master-openrc seaweedfs-filer-openrc seaweedfs-worker-openrc \ Local APK repository is ready.
| sort Repository: /repo
printf "\nSeaweedFS version:\n" Workspace: /work
weed version
printf "\nEntering %s. Repository mounted read-only at /work.\n\n" "${TEST_SHELL}" Examples:
apk add seaweedfs seaweedfs-master-openrc
apk add greptimedb greptimedb-docs greptimedb-standalone-openrc
apk add lavinmq lavinmq-openrc
apk add gitea gitea-openrc
Entering ${TEST_SHELL}.
EOF
exec "${TEST_SHELL}" exec "${TEST_SHELL}"
' '