The store build has its own id, so the native-messaging manifest refused it and the extension reported the app as not running. Chrome now allows the store id and the unpacked development id, in the NSIS hook and in both install scripts; --chrome-id / -ChromeId take a list. Co-Authored-By: Claude Opus 5.5 <[email protected]>
111 lines
4.4 KiB
Bash
Executable File
111 lines
4.4 KiB
Bash
Executable File
#!/bin/sh
|
|
# Registers the Kestrove native-messaging host with the browsers of the current user (Linux, macOS).
|
|
# Windows: install.ps1.
|
|
#
|
|
# install.sh [--nmh /path/to/kestrove-nmh] [--chrome-id ID[,ID…]] [--firefox-id ID]
|
|
# [--browsers chrome,chromium,edge,brave,firefox] [--user-data-dir DIR] [--uninstall]
|
|
#
|
|
# With neither --browsers nor --user-data-dir it installs for every browser whose profile directory exists.
|
|
# --user-data-dir adds a Chromium-style profile dir started with --user-data-dir (Chromium then
|
|
# looks for NativeMessagingHosts/ inside it), e.g. for tests.
|
|
# allowed_origins / allowed_extensions pin the host to our extension ids (docs/04 A8).
|
|
set -eu
|
|
|
|
HOST=app.kestrove.nmh
|
|
HERE=$(cd "$(dirname "$0")" && pwd)
|
|
NMH=""
|
|
# Chrome: the Chrome Web Store build, then the unpacked development build (pinned by the manifest key in
|
|
# kestrove-browser/scripts/build.mjs).
|
|
CHROME_IDS="pmhfoafjoogobhfadaicklhkldgnafmk kogapfibnnpeapfcjkkpgjddbhnjfein"
|
|
FIREFOX_ID=[email protected]
|
|
BROWSERS=""
|
|
USER_DATA_DIR=""
|
|
UNINSTALL=0
|
|
|
|
die() { echo "install.sh: $*" >&2; exit 1; }
|
|
|
|
while [ $# -gt 0 ]; do
|
|
case "$1" in
|
|
--nmh) NMH=$2; shift 2 ;;
|
|
--chrome-id) CHROME_IDS=$(echo "$2" | tr ',' ' '); shift 2 ;;
|
|
--firefox-id) FIREFOX_ID=$2; shift 2 ;;
|
|
--browsers) BROWSERS=$(echo "$2" | tr ',' ' '); shift 2 ;;
|
|
--user-data-dir) USER_DATA_DIR=$2; shift 2 ;;
|
|
--uninstall) UNINSTALL=1; shift ;;
|
|
-h|--help) sed -n '2,13p' "$0"; exit 0 ;;
|
|
*) die "unknown option $1" ;;
|
|
esac
|
|
done
|
|
|
|
for id in $CHROME_IDS; do echo "$id" | grep -Eq '^[a-p]{32}$' || die "--chrome-id must be 32 letters a-p"; done
|
|
# "chrome-extension://a/", "chrome-extension://b/" (the template supplies the outer quotes).
|
|
CHROME_ORIGINS=$(for id in $CHROME_IDS; do printf '%s' "${sep-}chrome-extension://$id/"; sep='", "'; done)
|
|
echo "$FIREFOX_ID" | grep -Eq '^[A-Za-z0-9._@{}-]+$' || die "bad --firefox-id"
|
|
|
|
if [ "$UNINSTALL" = 0 ]; then
|
|
if [ -z "$NMH" ]; then
|
|
# Next to this script (installed layout), else the cargo build output (development).
|
|
for c in "$HERE/kestrove-nmh" "$HERE/../src-tauri/target/release/kestrove-nmh" "$HERE/../src-tauri/target/debug/kestrove-nmh"; do
|
|
[ -x "$c" ] && NMH=$c && break
|
|
done
|
|
fi
|
|
[ -n "$NMH" ] || die "kestrove-nmh not found; pass --nmh"
|
|
[ -x "$NMH" ] || die "$NMH is not executable"
|
|
NMH=$(cd "$(dirname "$NMH")" && pwd)/$(basename "$NMH")
|
|
case "$NMH" in *[\"\\\|\&]*) die "the host path may not contain quotes, backslashes, | or &" ;; esac
|
|
fi
|
|
|
|
case "$(uname -s)" in
|
|
Darwin)
|
|
# The Kestrove Mac app registers its own host on launch; this points the browsers at a desktop dev build.
|
|
[ "$UNINSTALL" = 1 ] || echo "note: on macOS the Kestrove app registers itself; re-open it to switch back" >&2
|
|
BASE="$HOME/Library/Application Support"
|
|
dir_chrome="$BASE/Google/Chrome"
|
|
dir_chromium="$BASE/Chromium"
|
|
dir_edge="$BASE/Microsoft Edge"
|
|
dir_brave="$BASE/BraveSoftware/Brave-Browser"
|
|
dir_firefox="$BASE/Mozilla"
|
|
ff_sub=NativeMessagingHosts
|
|
;;
|
|
Linux)
|
|
CFG=${XDG_CONFIG_HOME:-$HOME/.config}
|
|
dir_chrome="$CFG/google-chrome"
|
|
dir_chromium="$CFG/chromium"
|
|
dir_edge="$CFG/microsoft-edge"
|
|
dir_brave="$CFG/BraveSoftware/Brave-Browser"
|
|
dir_firefox="$HOME/.mozilla"
|
|
ff_sub=native-messaging-hosts
|
|
;;
|
|
*) die "unsupported OS $(uname -s); on Windows use install.ps1" ;;
|
|
esac
|
|
|
|
# Auto-detect only when nothing was named: a test run with --user-data-dir must not touch real profiles.
|
|
[ -n "$BROWSERS$USER_DATA_DIR" ] || for b in chrome chromium edge brave firefox; do
|
|
eval "d=\$dir_$b"
|
|
[ -d "$d" ] && BROWSERS="$BROWSERS $b"
|
|
done
|
|
|
|
render() { # template → stdout
|
|
sed -e "s|__NMH_PATH__|$NMH|" -e "s|chrome-extension://__CHROME_EXTENSION_ID__/|$CHROME_ORIGINS|" -e "s|__FIREFOX_EXTENSION_ID__|$FIREFOX_ID|" "$HERE/$HOST.$1.json"
|
|
}
|
|
|
|
place() { # flavor dir
|
|
if [ "$UNINSTALL" = 1 ]; then
|
|
rm -f "$2/$HOST.json" && echo "removed $2/$HOST.json"
|
|
else
|
|
mkdir -p "$2"
|
|
render "$1" > "$2/$HOST.json.tmp" && chmod 644 "$2/$HOST.json.tmp" && mv "$2/$HOST.json.tmp" "$2/$HOST.json"
|
|
echo "installed $2/$HOST.json"
|
|
fi
|
|
}
|
|
|
|
for b in $BROWSERS; do
|
|
case "$b" in
|
|
chrome|chromium|edge|brave) eval "d=\$dir_$b"; place chrome "$d/NativeMessagingHosts" ;;
|
|
firefox) place firefox "$dir_firefox/$ff_sub" ;;
|
|
*) die "unknown browser $b" ;;
|
|
esac
|
|
done
|
|
[ -z "$USER_DATA_DIR" ] || place chrome "$USER_DATA_DIR/NativeMessagingHosts"
|
|
[ -n "$BROWSERS$USER_DATA_DIR" ] || echo "no supported browser profile found (use --browsers)"
|