Starten eines Terminalemulators ohne zu wissen, welche installiert sind

Starten eines Terminalemulators ohne zu wissen, welche installiert sind

Ich muss ein Skript schreiben, das einen Terminalemulator startet und darin einen bestimmten Befehl ausführt. Da ich nicht weiß, welche Terminalemulatoren auf dem Zielsystem installiert wurden, wie kann ich herausfinden, welche Terminalemulatoren installiert wurden?

Ich habe mir angesehendieser Thread. Ich bin jedoch nicht wirklich geneigt, eine fest codierte Prüfung durchzuführen, und suche nach einer allgemeinen Lösung.

Ich habe mir das ausgedachtsehrschmutziger Hack, aber ich bin wirklich nicht sicher, wie das hier abschneiden würde:

termdetect:

#!/bin/bash

IFS=:
for i in $PATH; do
  find "$i" -type f -exec isterminal {} \;
done

isterminal:

#!/bin/bash

if [[ ! -z "$1" ]]; then
  if [[ "$(head -c 4 "$1")" == $'\x7fELF' ]]; then
    if ! grep editor "$1" > /dev/null; then
      if grep -E '(vte_terminal_|libutempter|rxvt_)' "$1" > /dev/null; then
        echo "$1"
      fi
    fi
  fi
fi

Gibt es eine einfache generische Lösung, die ich vielleicht übersehe? Oder bleibt mir keine andere Möglichkeit, als Binärdateien nach Hinweisen zu durchsuchen oder eine fest codierte Liste zu verwenden?

Antwort1

Ihre Heuristik ist ziemlich schlecht. Hier ist, was sie auf einer meiner Debian-Wheezy-Maschinen finden (ich habe korrekte Treffer manuell mit einem markiert +).

/usr/bin/gcm-calibrate
/usr/bin/gnome-terminal        +
/usr/bin/mosh-client   
/usr/bin/mosh-server
/usr/bin/mrxvt                 +
/usr/bin/mrxvt-full            +
/usr/bin/roxterm               +
/usr/bin/rxvt-unicode          +
/usr/bin/urxvt                 +
/usr/bin/urxvtd
/usr/bin/vinagre
/usr/bin/x-terminal-emulator   +
/usr/bin/xfce4-terminal        +
/usr/bin/xterm                 +

Wenn Sie die erste alphabetische Übereinstimmung auswählen, handelt es sich um einen Farbkalibrator.

Hier ist die Liste der Alternativen für x-terminal-emulator, was auf diesem Debian-Rechner die richtige Antwort ist (soweit es distributionsverwaltete Programme betrifft):

/usr/bin/Eterm
/usr/bin/gnome-terminal.wrapper
/usr/bin/koi8rxterm
/usr/bin/konsole
/usr/bin/lxterm
/usr/bin/mlterm
/usr/bin/mrxvt-full
/usr/bin/roxterm
/usr/bin/rxvt-xpm
/usr/bin/rxvt-xterm
/usr/bin/urxvt
/usr/bin/uxterm
/usr/bin/xfce4-terminal.wrapper
/usr/bin/xterm
/usr/bin/xvt

Sie finden 7 von 15 (unter Berücksichtigung von Namensunklarheiten), was keine sehr gute Trefferquote ist.

Sie könnten versuchen, Ihre Heuristik zu verfeinern, aber das ist ein Spiel ohne Ende. Das Minimum wäre, nur ausführbare Dateien beizubehalten, die sowohl mit einigen X11-Bibliotheken verknüpft sind als auch eine Master-Terminalfunktion oder ein Dienstprogramm wie getptoder aufrufen grantpt, aber das wird zwangsläufig auch viele falsche Ergebnisse finden und ausführbare Dateien übersehen, bei denen der Aufruf in einer Bibliothek erfolgt (wie konsole). Und dies wird ausführbare Dateien mit nativem Code übersehen, auf die über einen Shell-Wrapper zugegriffen wird (es gibt mehrere in meiner Liste).

Anhand des ausführbaren Inhalts lässt sich nicht erkennen, ob es sich bei einem Programm um einen X-Terminal-Emulator handelt.

Das Erkennen von Programmen anhand ihres Namens ist eine weitaus bessere Heuristik.

Beachten Sie auch, dass verschiedene Programme eine unterschiedliche Befehlszeilensyntax haben. Die meisten akzeptieren und , haben aber unterschiedliche Parsing-Regeln (ob über eine Shell gelaufen wird oder nicht, ob mehrere Argumente akzeptiert werden oder nicht). Daher sollten Sie nach einen einzelnen Parameter übergeben , der keine Sonderzeichen der Shell enthält.-T TITLE-e COMMAND-e-e

Unter Debian und Derivatenx-terminal-emulatorist garantiert ein X-Terminalemulator, der -Tund unterstützt -e, sodass -ealle nachfolgenden Befehlszeilenparameter als Befehl und dessen Argument verwendet werden und keine Shell-Erweiterung auf ihnen durchgeführt wird. Da sich einige Emulatoren anders verhalten, x-terminal-emulatorist manchmal ein Wrapper, der eine eher xterm-ähnliche Syntax verwendet ( gnome-terminal.wrapperund xfce4-terminal.wrappersind zwei Beispiele dafür).

Ich kenne so etwas bei anderen Unix-Varianten nicht. Für Portabilität ist eine fest codierte Liste von Programmnamen die beste Lösung.

Darüber hinaus gibt Ihnen die Erkennung installierter Terminalemulatoren keinen Aufschluss über die Präferenzen des Benutzers. Wenn ich beispielsweise Gnome verwende, möchte ich wahrscheinlich nicht, dass Ihre Anwendung Konsole startet – es sei denn, ich bevorzuge zufällig Konsole, aber woher sollen Sie das wissen?

Der De-facto-Standard für Benutzereinstellungen ist überFreeDesktop.orgSpezifikationen. Freedesktop veröffentlicht einexdg-utilsPaket, das Programme enthält wiexdg-openum ein Dokument in der richtigen Anwendung zu öffnen,xdg-emailum die bevorzugte Anwendung zum Verfassen von E-Mails des Benutzers zu starten, und noch wichtigerxdg-terminalum den bevorzugten Terminalemulator des Benutzers zu öffnen.

Dies wäre xdg-terminaldas Richtige, und Sie sollten es verwenden, wenn es vorhanden ist. Leider xdg-terminalist es nicht überall verfügbar; Debian liefert es beispielsweise nicht mit (es ist einFehler bei langer Inaktivität). Außerdemxdg-terminallässt ein einzelnes Befehlsargument zu und ist nicht konsistent hinsichtlich der Art der Erweiterung, die dieses Argument erfährt.

Was auch immer Sie tun, stellen Sie sicher, dass der Anrufer eine einfache Möglichkeit hat, seine Präferenz anzugeben. Selbst xdg-terminaldas klappt nicht immer.

Daher ist Ihre beste Strategie:

  1. Wenn der Benutzer eine Präferenz angegeben hat, verwenden Sie diese
  2. sonst versuchenxdg-terminal
  3. sonst versuchenx-terminal-emulator
  4. andernfalls versuchen Sie es mit einer fest codierten Liste

Antwort2

Unter Debian und Derivaten (Ubuntu, Mint, …) x-terminal-emulatorwird immer das standardmäßige grafische Terminal des Administrators gestartet.
Sie können sogar so etwas einfügen, um festzustellen, ob es sich um eine grafische Sitzung handelt:

if [ -z "$XAUTHORITY" ]
then 
 echo "Failed to launch terminal emulator! This is not a graphical session."
else
 x-terminal-emulator
fi

verwandte Informationen