#!/bin/bash # --- Hardware iteration (live Pi at onefinity.local) --- # # Rsyncs the freshly built static UI tree (build/http/) onto the Pi's # bbctrl egg directory and restarts bbctrl. This is much faster than # a full firmware update and is the fastest way to iterate on the V09 # UI changes against real machine state (W axis, jog feedback, etc). # # Defaults: # HOST=onefinity.local # REMOTE_USER=bbmc # PASSWORD=onefinity (used for sudo on the Pi) # # Override: # HOST=10.1.10.55 ./deploy.sh hardware set -euo pipefail SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" cd "$SCRIPT_DIR" HOST="${HOST:-onefinity.local}" REMOTE_USER="${REMOTE_USER:-bbmc}" PASSWORD="${PASSWORD:-onefinity}" echo "Building UI bundle (HTML + resources)..." make build/http/index.html >/dev/null # Copy src/resources/* into build/http/. The Makefile's "all" target # also does this, but pulls in cross-compiled subprojects (avr/boot/ # pwr/jig) we don't have toolchains for on macOS. This rsync mirrors # only the resource tree. rsync -a src/resources/ build/http/ echo "Locating bbctrl http/ directory on $HOST..." REMOTE_HTTP_DIR="$(ssh -o ConnectTimeout=5 "${REMOTE_USER}@${HOST}" \ "ls -d /usr/local/lib/python*/dist-packages/bbctrl-*-py*.egg/bbctrl/http 2>/dev/null | head -1")" if [[ -z "$REMOTE_HTTP_DIR" ]]; then echo "ERROR: could not find bbctrl http/ directory on $HOST" exit 1 fi echo " $REMOTE_HTTP_DIR" echo "Rsyncing build/http/ -> $HOST:$REMOTE_HTTP_DIR/" # Stage to a tmp dir owned by $REMOTE_USER, then sudo-rsync into # place. This avoids needing root over rsync. We do NOT use --delete # anywhere -- the Pi's egg ships extra runtime files (config-template # .json, default machine JSON, buildbotics.nc, etc.) that come with # the bbctrl package and are not in this repo's src/resources. If # they were deleted the controller's API would 500 because Python # imports fail. REMOTE_TMP="/tmp/onefin_ui_$$" ssh -o ConnectTimeout=5 "${REMOTE_USER}@${HOST}" "mkdir -p '${REMOTE_TMP}'" rsync -avz \ --exclude='hostinfo.txt' \ -e "ssh -o ConnectTimeout=5" \ build/http/ "${REMOTE_USER}@${HOST}:${REMOTE_TMP}/" echo "Installing into ${REMOTE_HTTP_DIR}/ (sudo)..." ssh -o ConnectTimeout=5 "${REMOTE_USER}@${HOST}" \ "echo '${PASSWORD}' | sudo -S bash -c ' rsync -a --exclude=hostinfo.txt \"${REMOTE_TMP}/\" \"${REMOTE_HTTP_DIR}/\" \ && rm -rf \"${REMOTE_TMP}\" '" 2>&1 | tail -3 # Patch bbctrl Web.py so font files get the correct MIME type. The # Pi ships Python 3.5, whose `mimetypes` module doesn't know about # woff/woff2/ttf, so Tornado serves them as application/octet-stream # which Chromium 72 (the Pi's onboard browser) refuses to use as a # web font, leading to all FontAwesome icons rendering as empty # boxes in the kiosk UI. The patch is idempotent. echo "Patching bbctrl font MIME types (idempotent)..." scp -o ConnectTimeout=5 "$SCRIPT_DIR/scripts/deploy/patch_font_mime.py" \ "${REMOTE_USER}@${HOST}:/tmp/patch_font_mime.py" >/dev/null ssh -o ConnectTimeout=5 "${REMOTE_USER}@${HOST}" \ "echo '${PASSWORD}' | sudo -S python3 /tmp/patch_font_mime.py" 2>&1 | tail -3 echo "Restarting bbctrl service..." ssh -o ConnectTimeout=5 "${REMOTE_USER}@${HOST}" \ "echo '${PASSWORD}' | sudo -S systemctl restart bbctrl" 2>&1 | tail -3 echo "" echo "Deployed to http://${HOST}/" echo " Logs: ssh ${REMOTE_USER}@${HOST} 'journalctl -u bbctrl -f'" echo " Open: open -a 'Google Chrome' http://${HOST}/"