Skip to content

Commit a59da3f

Browse files
committed
ci: jenkinsfile for apk build
1 parent 9c484bf commit a59da3f

File tree

4 files changed

+383
-10
lines changed

4 files changed

+383
-10
lines changed

ci/Jenkinsfile.android

Lines changed: 129 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,129 @@
1+
#!/usr/bin/env groovy
2+
3+
4+
/* Options section can't access functions in objects. */
5+
def isPRBuild = utils.isPRBuild()
6+
def isNightlyBuild = utils.isNightlyBuild()
7+
8+
pipeline {
9+
agent {
10+
/* Image with Ubuntu 22.04, QT 6.9.0, Android SDK/NDK, Go, and Nim */
11+
docker {
12+
label 'linux'
13+
image 'statusteam/nim-status-client-build:1.0.0-qt6.9.0-android-ci'
14+
alwaysPull true
15+
}
16+
}
17+
18+
parameters {
19+
choice(
20+
name: 'ARCH',
21+
description: 'Target architecture',
22+
choices: ['arm64', 'x86_64']
23+
)
24+
booleanParam(
25+
name: 'RELEASE',
26+
description: 'Decides whether release credentials are used.',
27+
defaultValue: params.RELEASE ?: false
28+
)
29+
}
30+
31+
options {
32+
timestamps()
33+
/* Prevent Jenkins jobs from running forever */
34+
timeout(time: 45, unit: 'MINUTES')
35+
/* manage how many builds we keep */
36+
buildDiscarder(logRotator(
37+
numToKeepStr: '10',
38+
daysToKeepStr: '30',
39+
artifactNumToKeepStr: '3',
40+
))
41+
/* Allows combined build to copy */
42+
copyArtifactPermission('/status-desktop/*')
43+
/* Abort old PR builds. */
44+
disableConcurrentBuilds(abortPrevious: isPRBuild)
45+
disableRestartFromStage()
46+
}
47+
48+
environment {
49+
USE_SYSTEM_NIM = "1"
50+
GOCACHE = "/tmp/go-cache"
51+
GOMODCACHE = "/tmp/go-mod-cache"
52+
GOTMPDIR = "/tmp"
53+
STATUS_APK_ARTIFACT = "pkg/Status-tablet-${BUILD_NUMBER}.apk"
54+
}
55+
56+
stages {
57+
stage('Prepare') {
58+
steps {
59+
sh 'git submodule update --init --recursive'
60+
script {
61+
def qtPath = getQtAndroidPath(params.ARCH)
62+
env.QT_ANDROID_PATH = qtPath
63+
env.STATUS_APK = "/home/jenkins/workspace/status-desktop/systems/android/${params.ARCH}/package/mobile/bin/android/qt6/Status-tablet.apk"
64+
65+
echo "Building for architecture: ${params.ARCH}"
66+
echo "Qt Android path: ${qtPath}"
67+
}
68+
}
69+
}
70+
71+
stage('Build Android APK') {
72+
steps {
73+
sh """
74+
export ARCH="${params.ARCH}"
75+
export PKG_CONFIG_PATH="${env.QT_ANDROID_PATH}/lib/pkgconfig"
76+
export PATH="${env.QT_ANDROID_PATH}/bin:/opt/qt/6.9.0/gcc_64/bin:/opt/qt/6.9.0/gcc_64/libexec:${env.QT_ANDROID_PATH}/libexec:/opt/android-sdk/emulator:/opt/android-sdk/tools:/opt/android-sdk/tools/bin:/opt/android-sdk/platform-tools:${env.PATH}"
77+
make mobile-clean
78+
make -j${utils.getProcCount()} mobile-build V=3 USE_SYSTEM_NIM=1
79+
"""
80+
}
81+
}
82+
83+
stage('Package APK') {
84+
steps {
85+
sh """
86+
mkdir -p pkg
87+
cp '${env.STATUS_APK}' '${env.STATUS_APK_ARTIFACT}'
88+
ls -la '${env.STATUS_APK_ARTIFACT}'
89+
"""
90+
echo "APK packaged: ${env.STATUS_APK_ARTIFACT}"
91+
}
92+
}
93+
94+
stage('Parallel Upload') {
95+
parallel {
96+
stage('Upload') {
97+
steps {
98+
script {
99+
env.PKG_URL = s5cmd.upload(env.STATUS_APK_ARTIFACT)
100+
jenkins.setBuildDesc(APK: env.PKG_URL)
101+
}
102+
}
103+
}
104+
stage('Archive') {
105+
steps {
106+
archiveArtifacts env.STATUS_APK_ARTIFACT
107+
}
108+
}
109+
}
110+
}
111+
}
112+
113+
post {
114+
success { script { github.notifyPR(true) } }
115+
failure { script { github.notifyPR(false) } }
116+
cleanup { sh './scripts/clean-git.sh' }
117+
}
118+
}
119+
120+
def getQtAndroidPath(architecture) {
121+
switch(architecture) {
122+
case 'arm64':
123+
return '/opt/qt/6.9.0/android_arm64_v8a'
124+
case 'x86_64':
125+
return '/opt/qt/6.9.0/android_x86_64'
126+
default:
127+
return '/opt/qt/6.9.0/android_arm64_v8a'
128+
}
129+
}

ci/Jenkinsfile.qt-build

Lines changed: 50 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -116,23 +116,61 @@ pipeline {
116116
}
117117
}
118118

119-
stage('Test Image') {
119+
stage('Build Enhanced Runtime Image') {
120120
steps {
121121
script {
122-
echo "Testing the built image..."
122+
echo "Building enhanced runtime image with Nim and all tooling..."
123123
sh """
124-
docker run --rm \
125-
${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG} \
126-
"qmake --version"
127-
128-
docker run --rm \
129-
${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG} \
130-
"ls -la /opt/qt/${params.QT_VERSION}/"
124+
cd ${QT_BUILD_DIR}/nim-runtime
125+
docker build \
126+
--build-arg GOLANG_VERSION=1.23.10 \
127+
--build-arg NIM_VERSION=2.0.12 \
128+
--build-arg NIX_VERSION=2.24.11 \
129+
-t ${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}-ci .
131130
"""
132131
}
133132
}
134133
}
135134

135+
stage('Test Images') {
136+
parallel {
137+
stage('Test Qt Base Image') {
138+
steps {
139+
script {
140+
echo "Testing the Qt base image..."
141+
sh """
142+
docker run --rm \
143+
${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG} \
144+
"qmake --version"
145+
146+
docker run --rm \
147+
${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG} \
148+
"ls -la /opt/qt/${params.QT_VERSION}/"
149+
"""
150+
}
151+
}
152+
}
153+
154+
stage('Test Complete Image') {
155+
steps {
156+
script {
157+
echo "Testing the image with nim/go tooling..."
158+
sh """
159+
docker run --rm \
160+
${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}-ci \
161+
"qmake --version && nim --version && go version && echo 'All tools working!'"
162+
163+
docker run --rm \
164+
${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}-ci \
165+
"ls -la /home/jenkins/openssl-output/arm64-v8a/lib/"
166+
"""
167+
}
168+
}
169+
}
170+
}
171+
}
172+
173+
136174
stage('Push to DockerHub') {
137175
when {
138176
expression { params.PUSH_TO_DOCKERHUB == true }
@@ -149,6 +187,7 @@ pipeline {
149187
sh """
150188
echo \$DOCKER_PASS | docker login -u \$DOCKER_USER --password-stdin
151189
docker push ${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}
190+
docker push ${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}-ci
152191
docker logout
153192
"""
154193
}
@@ -167,7 +206,8 @@ pipeline {
167206
Qt Build Successful!
168207
- Qt Version: ${params.QT_VERSION}
169208
- Docker Tag: ${params.DOCKER_TAG}
170-
- Image: ${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}
209+
- Base Image: ${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}
210+
- Complete Image: ${DOCKER_REGISTRY}/${DOCKER_IMAGE_BASE}:${params.DOCKER_TAG}-ci
171211
"""
172212

173213
if (env.SLACK_WEBHOOK) {
Lines changed: 142 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,142 @@
1+
FROM statusteam/nim-status-client-build:1.0.0-qt6.9.0-android
2+
3+
ARG GOLANG_VERSION="1.23.10"
4+
ARG NIM_VERSION="2.0.12"
5+
ARG NIX_VERSION="2.24.11"
6+
7+
LABEL description="Complete Android build environment with Qt, Nim, and all tooling"
8+
LABEL qt.version="6.9.0"
9+
LABEL nim.version="${NIM_VERSION}"
10+
LABEL base.image="statusteam/nim-status-client-build:1.0.0-qt6.9.0-android"
11+
12+
ENV DEBIAN_FRONTEND=noninteractive
13+
14+
# Create jenkins user with specific UID/GID for compatibility
15+
RUN groupadd -g 1001 jenkins && useradd -r -g jenkins -m -d /home/jenkins -s /bin/bash -u 1001 jenkins
16+
17+
# Install additional runtime dependencies
18+
RUN apt-get update && apt-get install -y --no-install-recommends \
19+
curl \
20+
git \
21+
unzip \
22+
wget \
23+
build-essential \
24+
software-properties-common \
25+
gnupg2 \
26+
ca-certificates \
27+
locales \
28+
file \
29+
xz-utils \
30+
python3 \
31+
python3-pip \
32+
python3-venv \
33+
perl \
34+
sudo \
35+
pkg-config \
36+
cmake \
37+
ninja-build \
38+
libgl1-mesa-dev \
39+
libfontconfig1 \
40+
libdbus-1-3 \
41+
&& apt-get clean \
42+
&& rm -rf /var/lib/apt/lists/* \
43+
&& rm -rf /tmp/* \
44+
&& rm -rf /var/tmp/*
45+
46+
# Configure locales
47+
RUN sed -i '/en_US.UTF-8/s/^# //g' /etc/locale.gen && locale-gen
48+
ENV LANG=en_US.UTF-8
49+
ENV LANGUAGE=en_US:en
50+
ENV LC_ALL=en_US.UTF-8
51+
52+
# Give jenkins sudo access
53+
RUN echo "jenkins ALL=(ALL) NOPASSWD: ALL" >> /etc/sudoers
54+
55+
# Create nix directory
56+
RUN mkdir /nix && chown jenkins:jenkins /nix
57+
58+
# Install/Update Golang to the version we need
59+
RUN GOLANG_SHA256="535f9f81802499f2a7dbfa70abb8fda3793725fcc29460f719815f6e10b5fd60" \
60+
&& GOLANG_TARBALL="go${GOLANG_VERSION}.linux-amd64.tar.gz" \
61+
&& rm -rf /usr/local/go \
62+
&& wget -q "https://dl.google.com/go/${GOLANG_TARBALL}" \
63+
&& echo "${GOLANG_SHA256} ${GOLANG_TARBALL}" | sha256sum -c \
64+
&& tar -C /usr/local -xzf "${GOLANG_TARBALL}" \
65+
&& rm "${GOLANG_TARBALL}" \
66+
&& ln -sf /usr/local/go/bin/go /usr/local/bin/go \
67+
&& ln -sf /usr/local/go/bin/gofmt /usr/local/bin/gofmt
68+
69+
# Install Go tools as root first, then copy to accessible location
70+
RUN /usr/local/go/bin/go install github.com/go-bindata/go-bindata/v3/go-bindata@latest \
71+
&& /usr/local/go/bin/go install go.uber.org/mock/[email protected] \
72+
&& /usr/local/go/bin/go install google.golang.org/protobuf/cmd/[email protected] \
73+
&& cp /root/go/bin/* /usr/local/bin/ 2>/dev/null || true
74+
75+
# Configure Qt library path
76+
RUN echo "/opt/qt/6.9.0/gcc_64/lib" > /etc/ld.so.conf.d/qt.conf \
77+
&& ldconfig
78+
79+
# Create missing Qt Android directory for compatibility
80+
RUN mkdir -p /opt/qt/6.9.0/android_arm64_v8a/lib/pkgconfig
81+
82+
# Switch to jenkins user for user-specific installations
83+
USER jenkins
84+
WORKDIR /home/jenkins
85+
86+
# Build OpenSSL for Android arm64-v8a
87+
RUN set -e \
88+
&& git clone --depth 1 --branch openssl-3.0.15 https://github.com/openssl/openssl.git \
89+
&& mkdir -p openssl-output/arm64-v8a \
90+
&& cd openssl \
91+
&& echo "Building OpenSSL for arm64-v8a..." \
92+
&& export ANDROID_NDK_HOME=${ANDROID_NDK_ROOT} \
93+
&& export PATH=${ANDROID_NDK_ROOT}/toolchains/llvm/prebuilt/linux-x86_64/bin:$PATH \
94+
&& ./Configure android-arm64 \
95+
-D__ANDROID_API__=21 \
96+
--prefix=/home/jenkins/openssl-output/arm64-v8a \
97+
--openssldir=/home/jenkins/openssl-output/arm64-v8a \
98+
no-shared \
99+
no-tests \
100+
&& make -j$(($(nproc))) \
101+
&& make install_sw \
102+
&& make clean \
103+
&& echo "OpenSSL build completed"
104+
105+
# Install Nim
106+
RUN curl https://nim-lang.org/choosenim/init.sh -sSf | sh -s -- -y \
107+
&& /home/jenkins/.nimble/bin/choosenim ${NIM_VERSION}
108+
109+
# Install Nix
110+
RUN curl -s https://nixos.org/releases/nix/nix-${NIX_VERSION}/install | sh -s -- --no-daemon
111+
112+
# Install Go tools for jenkins user as well
113+
RUN /usr/local/go/bin/go install github.com/go-bindata/go-bindata/v3/go-bindata@latest \
114+
&& /usr/local/go/bin/go install go.uber.org/mock/[email protected]
115+
116+
# Switch back to root to create system-wide symlinks
117+
USER root
118+
119+
# Create symlinks for Nim tools
120+
RUN ln -sf /home/jenkins/.choosenim/toolchains/nim-${NIM_VERSION}/bin/nim /usr/local/bin/nim \
121+
&& ln -sf /home/jenkins/.choosenim/toolchains/nim-${NIM_VERSION}/bin/nimble /usr/local/bin/nimble \
122+
&& ln -sf /home/jenkins/.choosenim/toolchains/nim-${NIM_VERSION}/bin/choosenim /usr/local/bin/choosenim \
123+
&& chmod 755 /home/jenkins/.choosenim/toolchains/nim-${NIM_VERSION}/bin/* \
124+
&& chown -R root:root /home/jenkins/.choosenim/toolchains/nim-${NIM_VERSION}/bin
125+
126+
# Set comprehensive PATH with all tools
127+
ENV PATH="/opt/qt/6.9.0/gcc_64/bin:/opt/qt/6.9.0/android_arm64_v8a/bin:/usr/local/go/bin:/home/jenkins/go/bin:/opt/qt/6.9.0/gcc_64/libexec:/opt/android-sdk/cmdline-tools/latest/bin:/opt/android-sdk/platform-tools:/home/jenkins/.nix-profile/bin:/usr/local/bin:${PATH}"
128+
129+
# Set Qt and OpenSSL environment variables
130+
ENV QT_HOST_PATH="/opt/qt/6.9.0/gcc_64/"
131+
ENV QT_PLUGIN_PATH="/opt/qt/6.9.0/gcc_64/plugins"
132+
ENV OPENSSL_LIB_DIR="/home/jenkins/openssl-output/arm64-v8a/lib"
133+
ENV OPENSSL_INC_DIR="/home/jenkins/openssl-output/arm64-v8a/include"
134+
135+
# Switch back to jenkins user as default
136+
USER jenkins
137+
WORKDIR /home/jenkins
138+
139+
ENTRYPOINT ["/bin/bash", "-l", "-c"]
140+
141+
LABEL maintainer="status-team"
142+
LABEL source="https://github.com/status-im/status-desktop"

0 commit comments

Comments
 (0)