mirror of https://github.com/jetkvm/kvm.git
feat: add ci helper scripts
This commit is contained in:
parent
1a2b0ceae1
commit
b46139e18d
|
|
@ -18,22 +18,16 @@ jobs:
|
||||||
uses: actions/checkout@v5
|
uses: actions/checkout@v5
|
||||||
- name: Set up docker image context
|
- name: Set up docker image context
|
||||||
run: |
|
run: |
|
||||||
mkdir -p .docker
|
./scripts/ci_helper.sh prepare
|
||||||
cp \
|
|
||||||
Dockerfile.build \
|
|
||||||
go.mod \
|
|
||||||
go.sum \
|
|
||||||
.docker/
|
|
||||||
cp -r .devcontainer .docker/
|
|
||||||
- name: Set up Docker Buildx
|
- name: Set up Docker Buildx
|
||||||
uses: docker/setup-buildx-action@v3
|
uses: docker/setup-buildx-action@v3
|
||||||
- name: Build docker image
|
- name: Build docker image
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
context: .docker
|
context: ${{ env.DOCKER_BUILD_CONTEXT_DIR }}
|
||||||
file: .docker/Dockerfile.build
|
file: ${{ env.DOCKER_BUILD_CONTEXT_DIR }}/Dockerfile.build
|
||||||
push: false
|
push: false
|
||||||
tags: ghcr.io/jetkvm/buildkit:latest
|
tags: ${{ env.DOCKER_BUILD_TAG }}
|
||||||
- name: Set up Cmake cache
|
- name: Set up Cmake cache
|
||||||
uses: actions/cache@v4
|
uses: actions/cache@v4
|
||||||
with:
|
with:
|
||||||
|
|
@ -56,29 +50,13 @@ jobs:
|
||||||
make frontend
|
make frontend
|
||||||
- name: Build application inside Docker container
|
- name: Build application inside Docker container
|
||||||
run: |
|
run: |
|
||||||
docker run \
|
./scripts/ci_helper.sh make build_dev
|
||||||
--interactive \
|
|
||||||
--tty \
|
|
||||||
--rm \
|
|
||||||
--env JETKVM_INSIDE_DOCKER=1 \
|
|
||||||
-v "$(pwd):/build" \
|
|
||||||
-v "$(pwd)/.cache:/root/.cache/go-build" \
|
|
||||||
ghcr.io/jetkvm/buildkit:latest \
|
|
||||||
make build_dev
|
|
||||||
- name: Run tests
|
- name: Run tests
|
||||||
run: |
|
run: |
|
||||||
go test ./... -json > testreport.json
|
go test ./... -json > testreport.json
|
||||||
- name: Make test cases
|
- name: Make test cases
|
||||||
run: |
|
run: |
|
||||||
docker run \
|
./scripts/ci_helper.sh make build_dev_test
|
||||||
--interactive \
|
|
||||||
--tty \
|
|
||||||
--rm \
|
|
||||||
--env JETKVM_INSIDE_DOCKER=1 \
|
|
||||||
-v "$(pwd):/build" \
|
|
||||||
-v "$(pwd)/.cache:/root/.cache/go-build" \
|
|
||||||
ghcr.io/jetkvm/buildkit:latest \
|
|
||||||
make build_dev_test
|
|
||||||
- name: Golang Test Report
|
- name: Golang Test Report
|
||||||
uses: becheran/go-testreport@v0.3.2
|
uses: becheran/go-testreport@v0.3.2
|
||||||
with:
|
with:
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@ ENV GOTOOLCHAIN=local
|
||||||
ENV GOPATH=/go
|
ENV GOPATH=/go
|
||||||
ENV PATH=$GOPATH/bin:/usr/local/go/bin:$PATH
|
ENV PATH=$GOPATH/bin:/usr/local/go/bin:$PATH
|
||||||
|
|
||||||
COPY .devcontainer/install-deps.sh /install-deps.sh
|
COPY install-deps.sh /install-deps.sh
|
||||||
RUN /install-deps.sh
|
RUN /install-deps.sh
|
||||||
|
|
||||||
# Create build directory
|
# Create build directory
|
||||||
|
|
|
||||||
3
Makefile
3
Makefile
|
|
@ -45,10 +45,9 @@ build_native:
|
||||||
echo "libjknative.a already exists, skipping native build..."; \
|
echo "libjknative.a already exists, skipping native build..."; \
|
||||||
else \
|
else \
|
||||||
echo "Building native..."; \
|
echo "Building native..."; \
|
||||||
cd internal/native/cgo && ./ui_index.gen.sh && \
|
|
||||||
CC="$(BUILDKIT_PATH)/bin/$(BUILDKIT_FLAVOR)-gcc" \
|
CC="$(BUILDKIT_PATH)/bin/$(BUILDKIT_FLAVOR)-gcc" \
|
||||||
LD="$(BUILDKIT_PATH)/bin/$(BUILDKIT_FLAVOR)-ld" \
|
LD="$(BUILDKIT_PATH)/bin/$(BUILDKIT_FLAVOR)-ld" \
|
||||||
./build.sh; \
|
./scripts/build_cgo.sh; \
|
||||||
fi
|
fi
|
||||||
|
|
||||||
build_dev: build_native
|
build_dev: build_native
|
||||||
|
|
|
||||||
268
dev_deploy.sh
268
dev_deploy.sh
|
|
@ -1,268 +0,0 @@
|
||||||
#!/usr/bin/env bash
|
|
||||||
#
|
|
||||||
# Exit immediately if a command exits with a non-zero status
|
|
||||||
set -e
|
|
||||||
|
|
||||||
TERM="${TERM:-dumb}"
|
|
||||||
|
|
||||||
C_RST="$(tput sgr0)"
|
|
||||||
C_ERR="$(tput setaf 1)"
|
|
||||||
C_OK="$(tput setaf 2)"
|
|
||||||
C_WARN="$(tput setaf 3)"
|
|
||||||
C_INFO="$(tput setaf 5)"
|
|
||||||
|
|
||||||
msg() { printf '%s%s%s\n' $2 "$1" $C_RST; }
|
|
||||||
|
|
||||||
msg_info() { msg "$1" $C_INFO; }
|
|
||||||
msg_ok() { msg "$1" $C_OK; }
|
|
||||||
msg_err() { msg "$1" $C_ERR; }
|
|
||||||
msg_warn() { msg "$1" $C_WARN; }
|
|
||||||
|
|
||||||
# Function to display help message
|
|
||||||
show_help() {
|
|
||||||
echo "Usage: $0 [options] -r <remote_ip>"
|
|
||||||
echo
|
|
||||||
echo "Required:"
|
|
||||||
echo " -r, --remote <remote_ip> Remote host IP address"
|
|
||||||
echo
|
|
||||||
echo "Optional:"
|
|
||||||
echo " -u, --user <remote_user> Remote username (default: root)"
|
|
||||||
echo " --run-go-tests Run go tests"
|
|
||||||
echo " --run-go-tests-only Run go tests and exit"
|
|
||||||
echo " --skip-ui-build Skip frontend/UI build"
|
|
||||||
echo " --skip-native-build Skip native build"
|
|
||||||
echo " -i, --install Build for release and install the app"
|
|
||||||
echo " --help Display this help message"
|
|
||||||
echo
|
|
||||||
echo "Example:"
|
|
||||||
echo " $0 -r 192.168.0.17"
|
|
||||||
echo " $0 -r 192.168.0.17 -u admin"
|
|
||||||
}
|
|
||||||
|
|
||||||
# Default values
|
|
||||||
REMOTE_USER="root"
|
|
||||||
REMOTE_PATH="/userdata/jetkvm/bin"
|
|
||||||
SKIP_UI_BUILD=false
|
|
||||||
SKIP_UI_BUILD_RELEASE=0
|
|
||||||
SKIP_NATIVE_BUILD=0
|
|
||||||
RESET_USB_HID_DEVICE=false
|
|
||||||
LOG_TRACE_SCOPES="${LOG_TRACE_SCOPES:-jetkvm,cloud,websocket,native,jsonrpc}"
|
|
||||||
RUN_GO_TESTS=false
|
|
||||||
RUN_GO_TESTS_ONLY=false
|
|
||||||
INSTALL_APP=false
|
|
||||||
BUILD_IN_DOCKER=false
|
|
||||||
DOCKER_BUILD_DEBUG=false
|
|
||||||
DOCKER_BUILD_TAG=ghcr.io/jetkvm/buildkit:latest
|
|
||||||
|
|
||||||
# Parse command line arguments
|
|
||||||
while [[ $# -gt 0 ]]; do
|
|
||||||
case $1 in
|
|
||||||
-r|--remote)
|
|
||||||
REMOTE_HOST="$2"
|
|
||||||
shift 2
|
|
||||||
;;
|
|
||||||
-u|--user)
|
|
||||||
REMOTE_USER="$2"
|
|
||||||
shift 2
|
|
||||||
;;
|
|
||||||
--skip-ui-build)
|
|
||||||
SKIP_UI_BUILD=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--skip-native-build)
|
|
||||||
SKIP_NATIVE_BUILD=1
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--reset-usb-hid)
|
|
||||||
RESET_USB_HID_DEVICE=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--build-in-docker)
|
|
||||||
BUILD_IN_DOCKER=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--docker-build-debug)
|
|
||||||
DOCKER_BUILD_DEBUG=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--run-go-tests)
|
|
||||||
RUN_GO_TESTS=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--run-go-tests-only)
|
|
||||||
RUN_GO_TESTS_ONLY=true
|
|
||||||
RUN_GO_TESTS=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
-i|--install)
|
|
||||||
INSTALL_APP=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--help)
|
|
||||||
show_help
|
|
||||||
exit 0
|
|
||||||
;;
|
|
||||||
*)
|
|
||||||
echo "Unknown option: $1"
|
|
||||||
show_help
|
|
||||||
exit 1
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
done
|
|
||||||
|
|
||||||
# Verify required parameters
|
|
||||||
if [ -z "$REMOTE_HOST" ]; then
|
|
||||||
msg_err "Error: Remote IP is a required parameter"
|
|
||||||
show_help
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
# check if the current CPU architecture is x86_64
|
|
||||||
if [ "$(uname -m)" != "x86_64" ]; then
|
|
||||||
msg_warn "Warning: This script is only supported on x86_64 architecture"
|
|
||||||
BUILD_IN_DOCKER=true
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$BUILD_IN_DOCKER" = true ]; then
|
|
||||||
if [ "$JETKVM_INSIDE_DOCKER" = 1 ]; then
|
|
||||||
msg_err "Error: already running inside Docker"
|
|
||||||
exit
|
|
||||||
fi
|
|
||||||
|
|
||||||
BUILD_ARGS="--build-arg BUILDPLATFORM=linux/amd64"
|
|
||||||
if [ "$DOCKER_BUILD_DEBUG" = true ]; then
|
|
||||||
BUILD_ARGS="$BUILD_ARGS --progress=plain --no-cache"
|
|
||||||
fi
|
|
||||||
|
|
||||||
msg_info "Checking if Docker is available ..."
|
|
||||||
if ! command -v docker &> /dev/null; then
|
|
||||||
msg_err "Error: Docker is not installed"
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
msg_info "▶ Building build environment ..."
|
|
||||||
TMP_DIR=$(mktemp -d)
|
|
||||||
cp -r .devcontainer "${TMP_DIR}"
|
|
||||||
cp go.mod go.sum Dockerfile.build "${TMP_DIR}"
|
|
||||||
pushd "${TMP_DIR}" > /dev/null
|
|
||||||
docker build $BUILD_ARGS -t ${DOCKER_BUILD_TAG} -f Dockerfile.build .
|
|
||||||
popd > /dev/null
|
|
||||||
rm -rf "${TMP_DIR}"
|
|
||||||
fi
|
|
||||||
|
|
||||||
do_make() {
|
|
||||||
if [ "$BUILD_IN_DOCKER" = true ]; then
|
|
||||||
msg_info "▶ Building the project in Docker ..."
|
|
||||||
docker run \
|
|
||||||
--interactive \
|
|
||||||
--tty \
|
|
||||||
--rm \
|
|
||||||
--env JETKVM_INSIDE_DOCKER=1 \
|
|
||||||
-v "$(pwd):/build" \
|
|
||||||
-v "$(pwd)/.cache:/root/.cache/go-build" \
|
|
||||||
${DOCKER_BUILD_TAG} make "$@"
|
|
||||||
else
|
|
||||||
make "$@"
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
# Build the development version on the host
|
|
||||||
# When using `make build_release`, the frontend will be built regardless of the `SKIP_UI_BUILD` flag
|
|
||||||
if [[ "$SKIP_UI_BUILD" = false && "$JETKVM_INSIDE_DOCKER" != 1 ]]; then
|
|
||||||
msg_info "▶ Building frontend"
|
|
||||||
make frontend SKIP_UI_BUILD=0
|
|
||||||
SKIP_UI_BUILD_RELEASE=1
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$RUN_GO_TESTS" = true ]; then
|
|
||||||
msg_info "▶ Building go tests"
|
|
||||||
make build_dev_test
|
|
||||||
|
|
||||||
msg_info "▶ Copying device-tests.tar.gz to remote host"
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "cat > /tmp/device-tests.tar.gz" < device-tests.tar.gz
|
|
||||||
|
|
||||||
msg_info "▶ Running go tests"
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" ash << 'EOF'
|
|
||||||
set -e
|
|
||||||
TMP_DIR=$(mktemp -d)
|
|
||||||
cd ${TMP_DIR}
|
|
||||||
tar zxf /tmp/device-tests.tar.gz
|
|
||||||
./gotestsum --format=testdox \
|
|
||||||
--jsonfile=/tmp/device-tests.json \
|
|
||||||
--post-run-command 'sh -c "echo $TESTS_FAILED > /tmp/device-tests.failed"' \
|
|
||||||
--raw-command -- ./run_all_tests -json
|
|
||||||
|
|
||||||
GOTESTSUM_EXIT_CODE=$?
|
|
||||||
if [ $GOTESTSUM_EXIT_CODE -ne 0 ]; then
|
|
||||||
echo "❌ Tests failed (exit code: $GOTESTSUM_EXIT_CODE)"
|
|
||||||
rm -rf ${TMP_DIR} /tmp/device-tests.tar.gz
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
TESTS_FAILED=$(cat /tmp/device-tests.failed)
|
|
||||||
if [ "$TESTS_FAILED" -ne 0 ]; then
|
|
||||||
echo "❌ Tests failed $TESTS_FAILED tests failed"
|
|
||||||
rm -rf ${TMP_DIR} /tmp/device-tests.tar.gz
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "✅ Tests passed"
|
|
||||||
rm -rf ${TMP_DIR} /tmp/device-tests.tar.gz
|
|
||||||
EOF
|
|
||||||
|
|
||||||
if [ "$RUN_GO_TESTS_ONLY" = true ]; then
|
|
||||||
msg_info "▶ Go tests completed"
|
|
||||||
exit 0
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$INSTALL_APP" = true ]
|
|
||||||
then
|
|
||||||
msg_info "▶ Building release binary"
|
|
||||||
do_make build_release SKIP_NATIVE_IF_EXISTS=${SKIP_NATIVE_BUILD} SKIP_UI_BUILD=${SKIP_UI_BUILD_RELEASE}
|
|
||||||
|
|
||||||
# Copy the binary to the remote host as if we were the OTA updater.
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "cat > /userdata/jetkvm/jetkvm_app.update" < bin/jetkvm_app
|
|
||||||
|
|
||||||
# Reboot the device, the new app will be deployed by the startup process.
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "reboot"
|
|
||||||
else
|
|
||||||
msg_info "▶ Building development binary"
|
|
||||||
do_make build_dev SKIP_NATIVE_IF_EXISTS=${SKIP_NATIVE_BUILD} SKIP_UI_BUILD=${SKIP_UI_BUILD_RELEASE}
|
|
||||||
|
|
||||||
# Kill any existing instances of the application
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "killall jetkvm_app_debug || true"
|
|
||||||
|
|
||||||
# Copy the binary to the remote host
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "cat > ${REMOTE_PATH}/jetkvm_app_debug" < bin/jetkvm_app
|
|
||||||
|
|
||||||
if [ "$RESET_USB_HID_DEVICE" = true ]; then
|
|
||||||
msg_info "▶ Resetting USB HID device"
|
|
||||||
msg_warn "The option has been deprecated and will be removed in a future version, as JetKVM will now reset USB gadget configuration when needed"
|
|
||||||
# Remove the old USB gadget configuration
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "rm -rf /sys/kernel/config/usb_gadget/jetkvm/configs/c.1/hid.usb*"
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" "ls /sys/class/udc > /sys/kernel/config/usb_gadget/jetkvm/UDC"
|
|
||||||
fi
|
|
||||||
|
|
||||||
# Deploy and run the application on the remote host
|
|
||||||
ssh "${REMOTE_USER}@${REMOTE_HOST}" ash << EOF
|
|
||||||
set -e
|
|
||||||
|
|
||||||
# Set the library path to include the directory where librockit.so is located
|
|
||||||
export LD_LIBRARY_PATH=/oem/usr/lib:\$LD_LIBRARY_PATH
|
|
||||||
|
|
||||||
# Kill any existing instances of the application
|
|
||||||
killall jetkvm_app || true
|
|
||||||
killall jetkvm_app_debug || true
|
|
||||||
|
|
||||||
# Navigate to the directory where the binary will be stored
|
|
||||||
cd "${REMOTE_PATH}"
|
|
||||||
|
|
||||||
# Make the new binary executable
|
|
||||||
chmod +x jetkvm_app_debug
|
|
||||||
|
|
||||||
# Run the application in the background
|
|
||||||
PION_LOG_TRACE=${LOG_TRACE_SCOPES} ./jetkvm_app_debug | tee -a /tmp/jetkvm_app_debug.log
|
|
||||||
EOF
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "Deployment complete."
|
|
||||||
|
|
@ -0,0 +1 @@
|
||||||
|
scripts/dev_deploy.sh
|
||||||
|
|
@ -1,53 +0,0 @@
|
||||||
#!/bin/bash
|
|
||||||
set -e
|
|
||||||
|
|
||||||
C_RST="$(tput sgr0)"
|
|
||||||
C_ERR="$(tput setaf 1)"
|
|
||||||
C_OK="$(tput setaf 2)"
|
|
||||||
C_WARN="$(tput setaf 3)"
|
|
||||||
C_INFO="$(tput setaf 5)"
|
|
||||||
|
|
||||||
msg() { printf '%s%s%s\n' $2 "$1" $C_RST; }
|
|
||||||
|
|
||||||
msg_info() { msg "$1" $C_INFO; }
|
|
||||||
msg_ok() { msg "$1" $C_OK; }
|
|
||||||
msg_err() { msg "$1" $C_ERR; }
|
|
||||||
msg_warn() { msg "$1" $C_WARN; }
|
|
||||||
|
|
||||||
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
|
|
||||||
BUILD_DIR=${SCRIPT_DIR}/build
|
|
||||||
|
|
||||||
CMAKE_TOOLCHAIN_FILE=/opt/jetkvm-native-buildkit/rv1106-jetkvm-v2.cmake
|
|
||||||
CLEAN_ALL=${CLEAN_ALL:-0}
|
|
||||||
|
|
||||||
if [ "$CLEAN_ALL" -eq 1 ]; then
|
|
||||||
rm -rf "${BUILD_DIR}"
|
|
||||||
fi
|
|
||||||
|
|
||||||
TMP_DIR=$(mktemp -d)
|
|
||||||
pushd "${SCRIPT_DIR}" > /dev/null
|
|
||||||
|
|
||||||
msg_info "▶ Generating UI index"
|
|
||||||
./ui_index.gen.sh
|
|
||||||
|
|
||||||
msg_info "▶ Building native library"
|
|
||||||
VERBOSE=1 cmake -B "${BUILD_DIR}" \
|
|
||||||
-DCMAKE_SYSTEM_PROCESSOR=armv7l \
|
|
||||||
-DCMAKE_SYSTEM_NAME=Linux \
|
|
||||||
-DCMAKE_CROSSCOMPILING=1 \
|
|
||||||
-DCMAKE_TOOLCHAIN_FILE=$CMAKE_TOOLCHAIN_FILE \
|
|
||||||
-DLV_BUILD_USE_KCONFIG=ON \
|
|
||||||
-DLV_BUILD_DEFCONFIG_PATH=${SCRIPT_DIR}/lvgl_defconfig \
|
|
||||||
-DCONFIG_LV_BUILD_EXAMPLES=OFF \
|
|
||||||
-DCONFIG_LV_BUILD_DEMOS=OFF \
|
|
||||||
-DSKIP_GLIBC_NAMES=ON \
|
|
||||||
-DCMAKE_BUILD_TYPE=Release \
|
|
||||||
-DCMAKE_INSTALL_PREFIX="${TMP_DIR}"
|
|
||||||
|
|
||||||
msg_info "▶ Copying built library and header files"
|
|
||||||
cmake --build "${BUILD_DIR}" --target install
|
|
||||||
cp -r "${TMP_DIR}/include" ../
|
|
||||||
cp -r "${TMP_DIR}/lib" ../
|
|
||||||
rm -rf "${TMP_DIR}"
|
|
||||||
|
|
||||||
popd > /dev/null
|
|
||||||
Binary file not shown.
|
|
@ -0,0 +1,93 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# check if TERM is set
|
||||||
|
# though it's not the actual way to detect if TTY is available, it's a good enough approximation for our use case
|
||||||
|
HAS_TTY=true
|
||||||
|
if [ -z "$TERM" ] || [ "$TERM" = "dumb" ]; then
|
||||||
|
HAS_TTY=false
|
||||||
|
fi
|
||||||
|
|
||||||
|
# default colors
|
||||||
|
C_RST=$(echo -e "\e[0m")
|
||||||
|
C_ERR=$(echo -e "\e[31m")
|
||||||
|
C_OK=$(echo -e "\e[32m")
|
||||||
|
C_WARN=$(echo -e "\e[33m")
|
||||||
|
C_INFO=$(echo -e "\e[35m")
|
||||||
|
|
||||||
|
# if TTY is available, use colors
|
||||||
|
if [ "$HAS_TTY" = true ]; then
|
||||||
|
C_RST="$(tput sgr0)"
|
||||||
|
C_ERR="$(tput setaf 1)"
|
||||||
|
C_OK="$(tput setaf 2)"
|
||||||
|
C_WARN="$(tput setaf 3)"
|
||||||
|
C_INFO="$(tput setaf 5)"
|
||||||
|
fi
|
||||||
|
|
||||||
|
msg() { printf '%s%s%s\n' $2 "$1" $C_RST; }
|
||||||
|
|
||||||
|
msg_info() { msg "$1" $C_INFO; }
|
||||||
|
msg_ok() { msg "$1" $C_OK; }
|
||||||
|
msg_err() { msg "$1" $C_ERR; }
|
||||||
|
msg_warn() { msg "$1" $C_WARN; }
|
||||||
|
|
||||||
|
DOCKER_BUILD_TAG=${DOCKER_BUILD_TAG:-ghcr.io/jetkvm/buildkit:latest}
|
||||||
|
DOCKER_BUILD_DEBUG=${DOCKER_BUILD_DEBUG:-false}
|
||||||
|
DOCKER_BUILD_CONTEXT_DIR=${DOCKER_BUILD_CONTEXT_DIR:-$(mktemp -d)}
|
||||||
|
DOCKER_GO_CACHE_DIR=${DOCKER_GO_CACHE_DIR:-$(pwd)/.cache}
|
||||||
|
|
||||||
|
BUILD_IN_DOCKER=${BUILD_IN_DOCKER:-false}
|
||||||
|
|
||||||
|
|
||||||
|
function prepare_docker_build_context() {
|
||||||
|
msg_info "▶ Preparing docker build context ..."
|
||||||
|
cp .devcontainer/install-deps.sh \
|
||||||
|
go.mod \
|
||||||
|
go.sum \
|
||||||
|
Dockerfile.build \
|
||||||
|
"${DOCKER_BUILD_CONTEXT_DIR}"
|
||||||
|
}
|
||||||
|
|
||||||
|
function build_docker_image() {
|
||||||
|
if [ "$JETKVM_INSIDE_DOCKER" = 1 ]; then
|
||||||
|
msg_err "Error: already running inside Docker"
|
||||||
|
exit
|
||||||
|
fi
|
||||||
|
|
||||||
|
BUILD_ARGS="--build-arg BUILDPLATFORM=linux/amd64"
|
||||||
|
if [ "$DOCKER_BUILD_DEBUG" = true ]; then
|
||||||
|
BUILD_ARGS="$BUILD_ARGS --progress=plain --no-cache"
|
||||||
|
fi
|
||||||
|
|
||||||
|
msg_info "Checking if Docker is available ..."
|
||||||
|
if ! command -v docker &> /dev/null; then
|
||||||
|
msg_err "Error: Docker is not installed"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
prepare_docker_build_context
|
||||||
|
pushd "${DOCKER_BUILD_CONTEXT_DIR}" > /dev/null
|
||||||
|
msg_info "▶ Building docker image ..."
|
||||||
|
docker build $BUILD_ARGS -t ${DOCKER_BUILD_TAG} -f Dockerfile.build .
|
||||||
|
popd > /dev/null
|
||||||
|
}
|
||||||
|
|
||||||
|
function do_make() {
|
||||||
|
DOCKER_BUILD_ARGS="--rm"
|
||||||
|
if [ "$HAS_TTY" = true ]; then
|
||||||
|
DOCKER_BUILD_ARGS="$DOCKER_BUILD_ARGS --interactive --tty"
|
||||||
|
fi
|
||||||
|
if [ "$BUILD_IN_DOCKER" = true ]; then
|
||||||
|
msg_info "▶ Building the project in Docker ..."
|
||||||
|
set -x
|
||||||
|
docker run \
|
||||||
|
--env JETKVM_INSIDE_DOCKER=1 \
|
||||||
|
-v "$(pwd):/build" \
|
||||||
|
-v "${DOCKER_GO_CACHE_DIR}:/root/.cache/go-build" \
|
||||||
|
${DOCKER_BUILD_TAG} make "$@"
|
||||||
|
set +x
|
||||||
|
else
|
||||||
|
msg_info "▶ Building the project in host ..."
|
||||||
|
set -x
|
||||||
|
make "$@"
|
||||||
|
set +x
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,26 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
SCRIPT_PATH=$(realpath "$(dirname $(realpath "${BASH_SOURCE[0]}"))")
|
||||||
|
source ${SCRIPT_PATH}/build_utils.sh
|
||||||
|
|
||||||
|
# check if GITHUB_ENV is set
|
||||||
|
if [ -z "$GITHUB_ENV" ]; then
|
||||||
|
echo "GITHUB_ENV is not set"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$1" = "prepare" ]; then
|
||||||
|
prepare_docker_build_context
|
||||||
|
echo "DOCKER_BUILD_CONTEXT_DIR=$DOCKER_BUILD_CONTEXT_DIR" >> $GITHUB_ENV
|
||||||
|
echo "DOCKER_BUILD_TAG=$DOCKER_BUILD_TAG" >> $GITHUB_ENV
|
||||||
|
elif [ "$1" = "make" ]; then
|
||||||
|
BUILD_IN_DOCKER=true
|
||||||
|
# check if GO is available
|
||||||
|
if ! command -v go &> /dev/null; then
|
||||||
|
msg_info "Go is not available, will using default cache directory"
|
||||||
|
else
|
||||||
|
DOCKER_GO_CACHE_DIR=$(go env GOCACHE)
|
||||||
|
fi
|
||||||
|
do_make "${@:2}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
|
@ -0,0 +1,218 @@
|
||||||
|
#!/usr/bin/env bash
|
||||||
|
#
|
||||||
|
# Exit immediately if a command exits with a non-zero status
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Function to display help message
|
||||||
|
show_help() {
|
||||||
|
echo "Usage: $0 [options] -r <remote_ip>"
|
||||||
|
echo
|
||||||
|
echo "Required:"
|
||||||
|
echo " -r, --remote <remote_ip> Remote host IP address"
|
||||||
|
echo
|
||||||
|
echo "Optional:"
|
||||||
|
echo " -u, --user <remote_user> Remote username (default: root)"
|
||||||
|
echo " --run-go-tests Run go tests"
|
||||||
|
echo " --run-go-tests-only Run go tests and exit"
|
||||||
|
echo " --skip-ui-build Skip frontend/UI build"
|
||||||
|
echo " --skip-native-build Skip native build"
|
||||||
|
echo " -i, --install Build for release and install the app"
|
||||||
|
echo " --help Display this help message"
|
||||||
|
echo
|
||||||
|
echo "Example:"
|
||||||
|
echo " $0 -r 192.168.0.17"
|
||||||
|
echo " $0 -r 192.168.0.17 -u admin"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Default values
|
||||||
|
SCRIPT_PATH=$(realpath "$(dirname $(realpath "${BASH_SOURCE[0]}"))")
|
||||||
|
REMOTE_USER="root"
|
||||||
|
REMOTE_PATH="/userdata/jetkvm/bin"
|
||||||
|
SKIP_UI_BUILD=false
|
||||||
|
SKIP_UI_BUILD_RELEASE=0
|
||||||
|
SKIP_NATIVE_BUILD=0
|
||||||
|
RESET_USB_HID_DEVICE=false
|
||||||
|
LOG_TRACE_SCOPES="${LOG_TRACE_SCOPES:-jetkvm,cloud,websocket,native,jsonrpc}"
|
||||||
|
RUN_GO_TESTS=false
|
||||||
|
RUN_GO_TESTS_ONLY=false
|
||||||
|
INSTALL_APP=false
|
||||||
|
BUILD_IN_DOCKER=false
|
||||||
|
DOCKER_BUILD_DEBUG=false
|
||||||
|
DOCKER_BUILD_TAG=ghcr.io/jetkvm/buildkit:latest
|
||||||
|
|
||||||
|
# Parse command line arguments
|
||||||
|
while [[ $# -gt 0 ]]; do
|
||||||
|
case $1 in
|
||||||
|
-r|--remote)
|
||||||
|
REMOTE_HOST="$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
-u|--user)
|
||||||
|
REMOTE_USER="$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
--skip-ui-build)
|
||||||
|
SKIP_UI_BUILD=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--skip-native-build)
|
||||||
|
SKIP_NATIVE_BUILD=1
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--reset-usb-hid)
|
||||||
|
RESET_USB_HID_DEVICE=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--build-in-docker)
|
||||||
|
BUILD_IN_DOCKER=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--docker-build-debug)
|
||||||
|
DOCKER_BUILD_DEBUG=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--run-go-tests)
|
||||||
|
RUN_GO_TESTS=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--run-go-tests-only)
|
||||||
|
RUN_GO_TESTS_ONLY=true
|
||||||
|
RUN_GO_TESTS=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
-i|--install)
|
||||||
|
INSTALL_APP=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--help)
|
||||||
|
show_help
|
||||||
|
exit 0
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo "Unknown option: $1"
|
||||||
|
show_help
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
source ${SCRIPT_PATH}/build_utils.sh
|
||||||
|
|
||||||
|
# Verify required parameters
|
||||||
|
if [ -z "$REMOTE_HOST" ]; then
|
||||||
|
msg_err "Error: Remote IP is a required parameter"
|
||||||
|
show_help
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# check if the current CPU architecture is x86_64
|
||||||
|
if [ "$(uname -m)" != "x86_64" ]; then
|
||||||
|
msg_warn "Warning: This script is only supported on x86_64 architecture"
|
||||||
|
BUILD_IN_DOCKER=true
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$BUILD_IN_DOCKER" = true ]; then
|
||||||
|
build_docker_image
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Build the development version on the host
|
||||||
|
# When using `make build_release`, the frontend will be built regardless of the `SKIP_UI_BUILD` flag
|
||||||
|
if [[ "$SKIP_UI_BUILD" = false && "$JETKVM_INSIDE_DOCKER" != 1 ]]; then
|
||||||
|
msg_info "▶ Building frontend"
|
||||||
|
make frontend SKIP_UI_BUILD=0
|
||||||
|
SKIP_UI_BUILD_RELEASE=1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$RUN_GO_TESTS" = true ]; then
|
||||||
|
msg_info "▶ Building go tests"
|
||||||
|
make build_dev_test
|
||||||
|
|
||||||
|
msg_info "▶ Copying device-tests.tar.gz to remote host"
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "cat > /tmp/device-tests.tar.gz" < device-tests.tar.gz
|
||||||
|
|
||||||
|
msg_info "▶ Running go tests"
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" ash << 'EOF'
|
||||||
|
set -e
|
||||||
|
TMP_DIR=$(mktemp -d)
|
||||||
|
cd ${TMP_DIR}
|
||||||
|
tar zxf /tmp/device-tests.tar.gz
|
||||||
|
./gotestsum --format=testdox \
|
||||||
|
--jsonfile=/tmp/device-tests.json \
|
||||||
|
--post-run-command 'sh -c "echo $TESTS_FAILED > /tmp/device-tests.failed"' \
|
||||||
|
--raw-command -- ./run_all_tests -json
|
||||||
|
|
||||||
|
GOTESTSUM_EXIT_CODE=$?
|
||||||
|
if [ $GOTESTSUM_EXIT_CODE -ne 0 ]; then
|
||||||
|
echo "❌ Tests failed (exit code: $GOTESTSUM_EXIT_CODE)"
|
||||||
|
rm -rf ${TMP_DIR} /tmp/device-tests.tar.gz
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
TESTS_FAILED=$(cat /tmp/device-tests.failed)
|
||||||
|
if [ "$TESTS_FAILED" -ne 0 ]; then
|
||||||
|
echo "❌ Tests failed $TESTS_FAILED tests failed"
|
||||||
|
rm -rf ${TMP_DIR} /tmp/device-tests.tar.gz
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "✅ Tests passed"
|
||||||
|
rm -rf ${TMP_DIR} /tmp/device-tests.tar.gz
|
||||||
|
EOF
|
||||||
|
|
||||||
|
if [ "$RUN_GO_TESTS_ONLY" = true ]; then
|
||||||
|
msg_info "▶ Go tests completed"
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$INSTALL_APP" = true ]
|
||||||
|
then
|
||||||
|
msg_info "▶ Building release binary"
|
||||||
|
do_make build_release SKIP_NATIVE_IF_EXISTS=${SKIP_NATIVE_BUILD} SKIP_UI_BUILD=${SKIP_UI_BUILD_RELEASE}
|
||||||
|
|
||||||
|
# Copy the binary to the remote host as if we were the OTA updater.
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "cat > /userdata/jetkvm/jetkvm_app.update" < bin/jetkvm_app
|
||||||
|
|
||||||
|
# Reboot the device, the new app will be deployed by the startup process.
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "reboot"
|
||||||
|
else
|
||||||
|
msg_info "▶ Building development binary"
|
||||||
|
do_make build_dev SKIP_NATIVE_IF_EXISTS=${SKIP_NATIVE_BUILD} SKIP_UI_BUILD=${SKIP_UI_BUILD_RELEASE}
|
||||||
|
|
||||||
|
# Kill any existing instances of the application
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "killall jetkvm_app_debug || true"
|
||||||
|
|
||||||
|
# Copy the binary to the remote host
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "cat > ${REMOTE_PATH}/jetkvm_app_debug" < bin/jetkvm_app
|
||||||
|
|
||||||
|
if [ "$RESET_USB_HID_DEVICE" = true ]; then
|
||||||
|
msg_info "▶ Resetting USB HID device"
|
||||||
|
msg_warn "The option has been deprecated and will be removed in a future version, as JetKVM will now reset USB gadget configuration when needed"
|
||||||
|
# Remove the old USB gadget configuration
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "rm -rf /sys/kernel/config/usb_gadget/jetkvm/configs/c.1/hid.usb*"
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" "ls /sys/class/udc > /sys/kernel/config/usb_gadget/jetkvm/UDC"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Deploy and run the application on the remote host
|
||||||
|
ssh "${REMOTE_USER}@${REMOTE_HOST}" ash << EOF
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Set the library path to include the directory where librockit.so is located
|
||||||
|
export LD_LIBRARY_PATH=/oem/usr/lib:\$LD_LIBRARY_PATH
|
||||||
|
|
||||||
|
# Kill any existing instances of the application
|
||||||
|
killall jetkvm_app || true
|
||||||
|
killall jetkvm_app_debug || true
|
||||||
|
|
||||||
|
# Navigate to the directory where the binary will be stored
|
||||||
|
cd "${REMOTE_PATH}"
|
||||||
|
|
||||||
|
# Make the new binary executable
|
||||||
|
chmod +x jetkvm_app_debug
|
||||||
|
|
||||||
|
# Run the application in the background
|
||||||
|
PION_LOG_TRACE=${LOG_TRACE_SCOPES} ./jetkvm_app_debug | tee -a /tmp/jetkvm_app_debug.log
|
||||||
|
EOF
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "Deployment complete."
|
||||||
|
|
@ -3,18 +3,8 @@
|
||||||
# Exit immediately if a command exits with a non-zero status
|
# Exit immediately if a command exits with a non-zero status
|
||||||
set -e
|
set -e
|
||||||
|
|
||||||
C_RST="$(tput sgr0)"
|
SCRIPT_PATH=$(realpath "$(dirname $(realpath "${BASH_SOURCE[0]}"))")
|
||||||
C_ERR="$(tput setaf 1)"
|
source ${SCRIPT_PATH}/build_utils.sh
|
||||||
C_OK="$(tput setaf 2)"
|
|
||||||
C_WARN="$(tput setaf 3)"
|
|
||||||
C_INFO="$(tput setaf 5)"
|
|
||||||
|
|
||||||
msg() { printf '%s%s%s\n' $2 "$1" $C_RST; }
|
|
||||||
|
|
||||||
msg_info() { msg "$1" $C_INFO; }
|
|
||||||
msg_ok() { msg "$1" $C_OK; }
|
|
||||||
msg_err() { msg "$1" $C_ERR; }
|
|
||||||
msg_warn() { msg "$1" $C_WARN; }
|
|
||||||
|
|
||||||
# Get the latest release information
|
# Get the latest release information
|
||||||
msg_info "Getting latest release information ..."
|
msg_info "Getting latest release information ..."
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue