From 65f06e613180fe4205c57fc0056e4d35f1eb266c Mon Sep 17 00:00:00 2001 From: Neilpang Date: Sat, 9 Nov 2024 09:08:06 +0000 Subject: [PATCH] Update from base builder --- .github/tpl/README.tpl.md | 25 +++ .github/workflows/build.yml | 68 ++++++++ .github/workflows/manual.yml | 44 +++++ .github/workflows/readme.yml | 50 ++++++ build.sh | 314 +++++++++++++++++++++++++++++++++++ 5 files changed, 501 insertions(+) create mode 100644 .github/tpl/README.tpl.md create mode 100644 .github/workflows/build.yml create mode 100644 .github/workflows/manual.yml create mode 100644 .github/workflows/readme.yml create mode 100644 build.sh diff --git a/.github/tpl/README.tpl.md b/.github/tpl/README.tpl.md new file mode 100644 index 0000000..a97ccea --- /dev/null +++ b/.github/tpl/README.tpl.md @@ -0,0 +1,25 @@ + + +[![Build](https://github.com/vmactions/{{VM_OS_NAME}}-builder/actions/workflows/build.yml/badge.svg)](https://github.com/vmactions/{{VM_OS_NAME}}-builder/actions/workflows/build.yml) + +Latest: {{LATEST_TAG}} + + +The image builder for [{{VM_OS_NAME}}-vm](https://github.com/vmactions/{{VM_OS_NAME}}-vm) + + +How to use: + +1. Use the [manual.yml](.github/workflows/manual.yml) to build manually. + + Run the workflow manually, you will get a view-only webconsole from the output of the workflow, just open the link in your web browser. + + You will also get an interactive VNC connection port from the output, you can connect to the vm by any vnc client. + +2. Run the builder locally on your Ubuntu machine. + + Just clone the repo. and run: + ```bash + bash build.sh {{LATEST_CONF}} + ``` + diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml new file mode 100644 index 0000000..428dd0a --- /dev/null +++ b/.github/workflows/build.yml @@ -0,0 +1,68 @@ +name: "Build" +on: + push: + branches: + - '*' + paths: + - '*.sh' + - '.github/workflows/build.yml' + - '*.txt' + - 'conf/*' + - 'hooks/*' + pull_request: + branches: + - '*' + paths: + - '*.sh' + - '.github/workflows/build.yml' + - '*.txt' + - 'conf/*' + - 'hooks/*' + workflow_dispatch: + + release: + types: [ created ] + + +concurrency: + group: ${{ github.workflow }}-${{ github.ref }} + cancel-in-progress: true + + +jobs: + build: + strategy: + matrix: + os: ["202404"] + runs-on: ubuntu-24.04 + env: + SEC_VBOX : ${{ secrets.SEC_VBOX }} + steps: + - name: Free Disk Space (Ubuntu) + uses: jlumbroso/free-disk-space@main + with: + # this might remove tools that are actually needed, + # if set to "true" but frees about 6 GB + tool-cache: false + - uses: actions/checkout@v4 + - name: Creating Web console + uses: vmactions/cf-tunnel@v0 + id: tunnel + with: + protocol: http + port: 8000 + - run: | + bash build.sh conf/openindiana-${{ matrix.os }}.conf + - name: Upload Release Asset + if: "contains(github.ref, 'refs/tags/')" + id: upload-release-asset + uses: softprops/action-gh-release@v2 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + with: + files: | + openindiana-${{ matrix.os }}.qcow2.zst* + openindiana-${{ matrix.os }}-id_rsa.pub + openindiana-${{ matrix.os }}-host.id_rsa + + diff --git a/.github/workflows/manual.yml b/.github/workflows/manual.yml new file mode 100644 index 0000000..45262fd --- /dev/null +++ b/.github/workflows/manual.yml @@ -0,0 +1,44 @@ +name: "Manual" +on: + workflow_dispatch: + + +jobs: + build: + runs-on: ubuntu-24.04 + env: + DEBUG: 1 + NGROK_TOKEN : ${{ secrets.NGROK_TOKEN }} + SEC_VBOX : ${{ secrets.SEC_VBOX }} + steps: + - uses: actions/checkout@v4 + - name: Creating web console + uses: vmactions/cf-tunnel@v0 + id: tunnel + with: + protocol: http + port: 8000 + - name: Run vnc tunnel + id: test + uses: vmactions/ngrok-tunnel@v0 + with: + protocol: tcp + port: 5900 + - name: Sleep + run: | + for i in $(seq 1 10) ; do echo $i; sleep 1; done + latest=$(cat $(ls conf/openindiana-*.conf | tail -1) | grep VM_RELEASE | cut -d = -f 2) + echo "please loging to ssh below, and run:" + echo "=============================" + echo "bash build.sh conf/openindiana-$latest.conf" + echo "=============================" + touch /tmp/keepalive + + - uses: neilpang/debugger-action@master + + + + + + + diff --git a/.github/workflows/readme.yml b/.github/workflows/readme.yml new file mode 100644 index 0000000..a01c002 --- /dev/null +++ b/.github/workflows/readme.yml @@ -0,0 +1,50 @@ +name: "Update Readme" +on: + workflow_dispatch: + push: + branches: + - 'main' + paths: + - '.github/tpl/*' + - '.github/data/*' + - '.github/workflows/readme.yml' + + release: + types: [ published ] + + +jobs: + readme: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + + - name: Get latest release + id: get-latest-release + uses: InsonusK/get-latest-release@v1.0.1 + with: + myToken: ${{ github.token }} + view_top: 1 + + - name: Using main branch + run: | + git switch main || (git fetch --all && git checkout -b main origin/main) + echo "LATEST_MAJOR=$(echo ${{ steps.get-latest-release.outputs.tag_name }} | cut -d . -f 1)" >> $GITHUB_ENV + echo "LATEST_TAG=${{ steps.get-latest-release.outputs.tag_name }}" >> $GITHUB_ENV + latest=$(ls conf/*.conf | tail -1) + echo "LATEST_CONF=$latest" >> $GITHUB_ENV + + - name: Update the readme.md + uses: vmactions/render@v0.0.1 + with: + datafile: .github/data/datafile.ini + files: | + .github/tpl/README.tpl.md : README.md + + - uses: EndBug/add-and-commit@v9 + with: + message: "Update version to ${{ steps.get-latest-release.outputs.tag_name }}" + pull: '--rebase --autostash ' + add: | + README.md + diff --git a/build.sh b/build.sh new file mode 100644 index 0000000..f68b6b8 --- /dev/null +++ b/build.sh @@ -0,0 +1,314 @@ +#!/usr/bin/env bash + +set -ex + + +_conf="$1" + +if [ -z "$_conf" ] ; then + echo "Please give the conf file" + exit 1 +fi + + +. "$_conf" + + +############################################################## +osname="$VM_OS_NAME" +ostype="$VM_OS_TYPE" +sshport=$VM_SSH_PORT + + +opts="$VM_OPTS" + +vboxlink="${SEC_VBOX:-$VM_VBOX_LINK}" + + +vmsh="$VM_VBOX" + + +export VM_OS_NAME +export VM_RELEASE +export VM_OCR +export VM_DISK +export VM_ARCH + + +############################################################## + + +waitForText() { + _text="$1" + $vmsh waitForText $osname "$_text" +} + +#keys splitted by ; +#eg: enter +#eg: down; enter +#eg: down; up; tab; enter + + +inputKeys() { + $vmsh input $osname "$1" +} + + + +if [ ! -e "$vmsh" ] ; then + echo "Downloading $vboxlink" + wget -O "$vmsh" "$vboxlink" +fi + +chmod +x "$vmsh" + + + +$vmsh startWeb $osname "needOCR" + + +$vmsh setup "needOCR" + +if ! $vmsh clearVM $osname; then + echo "vm does not exists" +fi + + +if [ "$VM_ISO_LINK" ]; then + $vmsh createVM $VM_ISO_LINK $osname $ostype $sshport + + sleep 2 + + if [ -e "hooks/installOpts.sh" ]; then + echo "hooks/installOpts.sh" + cat "hooks/installOpts.sh" + . "hooks/installOpts.sh" + else + $vmsh processOpts $osname "$opts" + + echo "sleep 60 seconds. just wait" + sleep 60 + + if $vmsh isRunning $osname; then + if ! $vmsh shutdownVM $osname; then + echo "shutdown error" + fi + if ! $vmsh destroyVM $osname; then + echo "destroyVM error" + fi + fi + fi + + while $vmsh isRunning $osname; do + sleep 5 + done + +elif [ "$VM_VHD_LINK" ]; then + if [ ! -e "$osname.qcow2" ]; then + if [ ! -e "$osname.qcow2.xz" ]; then + $vmsh download "$VM_VHD_LINK" $osname.qcow2.xz + fi + xz -d -T 0 --verbose "$osname.qcow2.xz" + fi + + $vmsh createVMFromVHD $osname $ostype $sshport + + sleep 5 + +else + echo "no VM_ISO_LINK or VM_VHD_LINK, can not build." + exit 1 +fi + + +echo "VM image size immediately after install:" +ls -lh + + +start_and_wait() { + $vmsh startVM $osname + sleep 2 + if [ -e "hooks/waitForLoginTag.sh" ]; then + echo "hooks/waitForLoginTag.sh" + cat "hooks/waitForLoginTag.sh" + . "hooks/waitForLoginTag.sh" + else + waitForText "$VM_LOGIN_TAG" + fi + + sleep 3 +} + +shutdown_and_wait() { + ssh $osname "$VM_SHUTDOWN_CMD" + + sleep 30 + + if $vmsh isRunning $osname; then + if ! $vmsh shutdownVM $osname; then + echo "shutdown error" + fi + fi + + while $vmsh isRunning $osname; do + sleep 5 + done +} + +restart_and_wait() { + shutdown_and_wait + start_and_wait +} + +############################################### + +start_and_wait + +inputKeys "string root; enter; sleep 1;" +if [ "$VM_ROOT_PASSWORD" ]; then + inputKeys "string $VM_ROOT_PASSWORD ; enter" +fi +inputKeys "enter" +sleep 2 + + +if [ ! -e ~/.ssh/id_rsa ] ; then + ssh-keygen -f ~/.ssh/id_rsa -q -N "" +fi + +cat enablessh.txt >enablessh.local + + +#add ssh key twice, to avoid bugs. +echo "echo '$(base64 -w 0 ~/.ssh/id_rsa.pub)' | openssl base64 -d >>~/.ssh/authorized_keys" >>enablessh.local +echo "" >>enablessh.local + +echo "echo '$(cat ~/.ssh/id_rsa.pub)' >>~/.ssh/authorized_keys" >>enablessh.local +echo "" >>enablessh.local + + +echo >>enablessh.local +echo "chmod 600 ~/.ssh/authorized_keys">>enablessh.local +echo "exit">>enablessh.local +echo >>enablessh.local + + +$vmsh inputFile $osname enablessh.local + + +############################################################### + +$vmsh addSSHHost $osname + + +ssh $osname sh <.ssh/config + +echo "Host host" >>.ssh/config +echo " HostName 192.168.122.1" >>.ssh/config +echo " User runner" >>.ssh/config +echo " ServerAliveInterval 1" >>.ssh/config + +EOF + +############################################################### + +if [ -e "hooks/postBuild.sh" ]; then + echo "hooks/postBuild.sh" + cat "hooks/postBuild.sh" + ssh $osname sh<"hooks/postBuild.sh" + + # Reboot here, possible there were system updates done that need + # a reboot to take effect before more operations can be done + restart_and_wait +fi + +ssh $osname 'cat ~/.ssh/id_rsa.pub' >$osname-$VM_RELEASE-id_rsa.pub + +#upload reboot.sh +if [ -e "hooks/reboot.sh" ]; then + echo "hooks/reboot.sh" + cat "hooks/reboot.sh" + scp hooks/reboot.sh $osname:/reboot.sh +else + ssh "$osname" "cat - >/reboot.sh" <$osname.rebooted + +END + +EOF +fi + +#set cronjob +ssh "$osname" sh </dev/null; then +crontab -l | { cat; echo "* * * * * /reboot.sh"; } | crontab -- +else +crontab -l | { cat; echo "@reboot /reboot.sh"; } | crontab - +fi +crontab -l + +EOF + + +# Install any requested packages +if [ "$VM_PRE_INSTALL_PKGS" ]; then + echo "$VM_INSTALL_CMD $VM_PRE_INSTALL_PKGS" + ssh $osname sh <<<"$VM_INSTALL_CMD $VM_PRE_INSTALL_PKGS" +fi + +if [ -e "hooks/finalize.sh" ]; then + echo "hooks/finalize.sh" + cat "hooks/finalize.sh" + ssh $osname sh<"hooks/finalize.sh" +fi + +# Done! +shutdown_and_wait + +############################################################## + +if [ "$VM_ISO_LINK" ]; then + echo "Clean up ISO for more space" + sudo rm -f ${osname}.iso +fi + +echo "contents of home directory:" +ls -lah + +echo "free space:" +df -h + +ova="$osname-$VM_RELEASE.qcow2" +echo "Exporting $ova" +$vmsh exportOVA $osname "$ova" + +cp ~/.ssh/id_rsa $osname-$VM_RELEASE-host.id_rsa + +echo "contents after export:" +ls -lah + + +############################################################## + +echo "Checking the packages: $VM_RSYNC_PKG $VM_SSHFS_PKG" + +if [ -z "$VM_RSYNC_PKG$VM_SSHFS_PKG" ]; then + echo "skip" +else + $vmsh addSSHAuthorizedKeys $osname-$VM_RELEASE-id_rsa.pub + $vmsh startVM $osname + $vmsh waitForVMReady $osname + if [ "$VM_RSYNC_PKG" ]; then + ssh $osname sh <<<"$VM_INSTALL_CMD $VM_RSYNC_PKG" + fi + if [ "$VM_SSHFS_PKG" ]; then + ssh $osname sh <<<"$VM_INSTALL_CMD $VM_SSHFS_PKG" + fi +fi + +