Created
September 14, 2015 18:27
-
-
Save ssokolow/894f5053afeebe57d249 to your computer and use it in GitHub Desktop.
Script to perform a web search in the user's default browser using the user's default search provider
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/sh | |
# Script to launch a search in the user's default browser using their default | |
# search provider. (Best effort, given that | |
# | |
# There may be a ready-made way to do most of this, but I don't know it so I | |
# just implemented the spec. | |
# http://standards.freedesktop.org/basedir-spec/basedir-spec-latest.html | |
# Helpers for useful error handling | |
die() { | |
xmessage "FATAL: $1" & | |
exit "$2" | |
} | |
require() { | |
if [ -z "$1" ]; then | |
die "$2" "$3" | |
fi | |
} | |
# Linux has `xdg-open <URL>` as an equivalent to `start <URL>` on Windows and | |
# `open <URL>` on OSX but, like those commands, it's completely confused by | |
# receiving `? <search term>` as an argument, so we manually figure out what | |
# command to call... | |
# Look up the .desktop application definition file associated with http:// URLs | |
xdg_name="$(xdg-mime query default x-scheme-handler/http)" | |
require "$xdg_name" "No association for http:// URLs" 1 | |
# Since most Linux desktops have SOMETHING GTK+-based, we could normally just | |
# use `gtk-launch "$xdg_name" "whatever"` here and call it done for the vast | |
# majority of Linux desktops, but Firefox requires --search rather than a | |
# leading ? and gtk-launch escapes that. | |
# Construct the search path | |
usrdata="${XDG_DATA_HOME:-$HOME/.local/share}" | |
sysdata="${XDG_DATA_DIRS:-/usr/local/share/:/usr/share/}" | |
data_dirs="$usrdata:$sysdata" | |
# Resolve the .desktop file name using the search path | |
OLD_IFS="$IFS" | |
IFS=":" | |
for datadir in $data_dirs; do | |
candidate="$datadir/applications/$xdg_name" | |
if [ -e "$candidate" ]; then | |
found="$candidate" | |
break | |
fi | |
done | |
IFS="$OLD_IFS" | |
unset OLD_IFS | |
require "$found" "Could not find http:// URL handler: $xdg_name" 2 | |
# Parse the raw command string out of the .desktop file | |
# (Not perfect, since it strips the % substitution placeholders rather than | |
# obeying them, but perfectly fine for this restricted use case) | |
app_path="$(grep '^Exec' "$found" | | |
head -1 | | |
sed 's/^Exec=//' | | |
sed 's/%.//')" | |
require "$app_path" "Could not parse Exec line from $found" 3 | |
# Open browser, special-casing every browser I tested which didn't like "? ..." | |
case "$xdg_name" in | |
*arora*) die "FATAL: Can't trigger default search provider in Arora" 4;; | |
*firefox*) $app_path --search "$*";; | |
*konqueror*) $app_path "$*";; | |
*luakit*) $app_path "$*";; | |
*midori*) die "FATAL: Can't trigger default search provider in Midori" 4;; | |
*) $app_path "? $*";; | |
esac |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment