geobridge/geobridge.sh
randogoth 6d18b36ab5 init
2026-01-12 21:19:33 +02:00

126 lines
3.2 KiB
Bash
Executable file

#!/bin/sh
# SPDX-License-Identifier: AGPL-3.0-or-later
# Copyright 2024 Jacob D Ludvigsen (contributions@ingeniorskap.no)
# https://gitlab.com/papiris/geobridge
# MODIFIED 2026 ethical_haquer
# https://github.com/waydroid/waydroid/issues/226#issuecomment-3733805954
# optimization and devbox setup additions by randogoth
# This script bridges basic geolocation info
# from Geoclue-2 running on the host system into Waydroid.
# Current location is parsed from the example "where-am-i" geoclue agent,
# and sent via adb to the mock location provider "appium"
# running in the Waydroid container.
find_where_am_i() {
# prefer PATH, then common locations (Nix and FHS installs)
if command -v where-am-i >/dev/null 2>&1; then
command -v where-am-i
return 0
fi
for candidate in \
/usr/libexec/geoclue-2.0/demos/where-am-i \
/nix/store/*geoclue*/libexec/geoclue-2.0/demos/where-am-i
do
if [ -x "$candidate" ]; then
printf '%s\n' "$candidate"
return 0
fi
done
return 1
}
extract_number() {
# return first numeric value from a line, stripping units/symbols
printf '%s\n' "$1" | awk '{
for (i = 1; i <= NF; i++) {
candidate = $i
gsub(/[^0-9.+-]/, "", candidate)
if (candidate ~ /^-?[0-9]+(\.[0-9]+)?$/) {
print candidate
exit
}
}
}'
}
if [ "$1" = "--init" ]; then
# make sure you've connected host system adb to the Waydroid container before running this program
# download appium settings android app
wget https://github.com/appium/io.appium.settings/releases/download/v7.0.10/settings_apk-debug.apk \
-O /tmp/appium.apk
# install appium in Waydroid container,
# don't grant permissions
waydroid app install /tmp/appium.apk
# allow to set Android location via api
adb shell settings put global hidden_api_policy 1
# allow appium to set mock location
adb shell appops set io.appium.settings \
android:mock_location allow
# allow appium access to location data
adb shell pm grant io.appium.settings \
android.permission.ACCESS_FINE_LOCATION
echo initialized
fi
lat=
long=
alt=
where_am_i="$(find_where_am_i)" || {
echo "Cannot find where-am-i demo agent; install geoclue demo or adjust path." >&2
exit 1
}
while true
do
# long-running command
"$where_am_i" \
--timeout=30 \
--accuracy-level=8 |
while IFS= read -r line
do
# parse output from geoclue agent
case "$line" in
(New*)
lat=
long=
alt=
;;
(Latitude:*)
lat="$(extract_number "$line")"
;;
(Longitude:*)
long="$(extract_number "$line")"
;;
(Altitude:*)
alt="$(extract_number "$line")"
;;
esac
# check that all location values have been assigned
if [ -n "$long" ] && [ -n "$lat" ]; then
alt="${alt:-0}"
# start/update appium service in Waydroid container with location
adb shell am start-foreground-service --user 0 \
-n io.appium.settings/.LocationService \
--es longitude "$long" \
--es latitude "$lat" \
--es altitude "$alt" > /dev/null
echo "Location updated: $lat, $long (alt $alt)"
lat=
long=
alt=
fi
done
done