Wie ändere ich die Standard-App für alle Dateien eines bestimmten Dateityps über das Terminal in OS X?

32

Wie kann ich die Standard-App für alle Dateien eines bestimmten Dateityps über das Terminal in OS X ändern?

Yashodhan
quelle
Kein Betrüger, obwohl ich es dort irgendwie beantwortet habe. Das tut mir leid.
Daniel Beck
Für den Stromverbrauch gefällt mir die akzeptierte Antwort unter einer neueren Super-User-Frage: Gibt es eine schnellere Möglichkeit, Standard-Apps für Dateitypen unter OS X zu ändern? . Der Einfachheit halber mag ich Daniels Antwort unten .
Graham Perrin

Antworten:

39

Ich habe einen einfacheren Weg. Du wirst Homebrew wollen, wenn du es noch nicht hast:

/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"

Installieren Sie duti:

brew install duti

Jetzt müssen Sie die ID der App finden, die Sie verwenden möchten, und sie der Erweiterung zuweisen, für die Sie sie verwenden möchten. In diesem Beispiel verwende ich bereits Brackets für *.shund möchte es auch für *.mdDateien anstelle von xcode verwenden.

Rufen Sie die Standard-App-ID für .shDateien ab:

duti -x sh

output:
  Brackets.app
  /opt/homebrew-cask/Caskroom/brackets/1.6/Brackets.app
  io.brackets.appshell

Die letzte Zeile ist die ID.

Verwenden Sie diese App-ID für alle .mdDateien:

duti -s io.brackets.appshell .md all
matte Verbrennungen
quelle
3
Würde dies 50 Mal bewerten, wenn ich könnte. Tolle Infos. Arbeitete wie ein Zauber für mich in El Capitan.
Ryan Walls
1
Auch in Sierra arbeiten. Zusätzlicher Tipp: UTIs sind schmerzhaft, aber Sie können "mdls -name kMDItemContentType <file>" verwenden, um die UTI für eine bestimmte Datei (und damit die Erweiterung) zu ermitteln.
Adrian
2
Wenn Sie noch keine App auf diese Weise mit einer App verknüpft haben, aber den Namen Ihrer App kennen, können Sie osascript -e 'id of app "$appName"'die ID jeder App ermitteln, die auf Ihrem System installiert ist
GrayedFox
1
Nur als Referenz: Tipp von @GrayedFox mit duti kombinieren:duti -s $(osascript -e 'id of app "Visual Studio Code"') .md all
Strajk
18

Bearbeiten ~/Library/Preferences/com.apple.LaunchServices.plist.

Fügen Sie unter einen Eintrag hinzu LSHandlers, der die UTI ( LSHandlerContentTypez. B. Schlüssel public.plain-text) und die Anwendungspaket-ID ( LSHandlerRoleAllz com.macromates.textmate. B. ) enthält.

Es sieht so aus in Eigenschaftenlisten-Editor aus :

Alt-Text Alt-Text

Verwenden Sie dazu in der Befehlszeile defaultsoder /usr/libexec/PlistBuddy. Beide haben umfangreiche Hilfeseiten.

Zum Beispiel, um alle .plistDateien mit zu öffnenXcode :

defaults write com.apple.LaunchServices LSHandlers -array-add '{ LSHandlerContentType = "com.apple.property-list"; LSHandlerRoleAll = "com.apple.dt.xcode"; }'

Natürlich müssen Sie sicherstellen, dass noch kein Eintrag für die UTI com.apple.property-listvorhanden ist.

Hier ist ein vollständigeres Skript, mit dem vorhandene Einträge für eine UTI entfernt und neue hinzugefügt werden. Es kann nur Bündel-IDs anstelle von Parametern verarbeiten LSHandlerContentTypeund wird immer festgelegt LSHandlerRoleAllund verfügt über fest codierte Bündel-IDs. Ansonsten sollte es ganz gut funktionieren.

#!/usr/bin/env bash

PLIST="$HOME/Library/Preferences/com.apple.LaunchServices.plist"
BUDDY=/usr/libexec/PlistBuddy

# the key to match with the desired value
KEY=LSHandlerContentType

# the value for which we'll replace the handler
VALUE=public.plain-text

# the new handler for all roles
HANDLER=com.macromates.TextMate

$BUDDY -c 'Print "LSHandlers"' $PLIST >/dev/null 2>&1
ret=$?
if [[ $ret -ne 0 ]] ; then
        echo "There is no LSHandlers entry in $PLIST" >&2
        exit 1
fi

function create_entry {
        $BUDDY -c "Add LSHandlers:$I dict" $PLIST
        $BUDDY -c "Add LSHandlers:$I:$KEY string $VALUE" $PLIST
        $BUDDY -c "Add LSHandlers:$I:LSHandlerRoleAll string $HANDLER" $PLIST
}

declare -i I=0
while [ true ] ; do
        $BUDDY -c "Print LSHandlers:$I" $PLIST >/dev/null 2>&1
        [[ $? -eq 0 ]] || { echo "Finished, no $VALUE found, setting it to $HANDLER" ; create_entry ; exit ; }

        OUT="$( $BUDDY -c "Print 'LSHandlers:$I:$KEY'" $PLIST 2>/dev/null )"
        if [[ $? -ne 0 ]] ; then 
                I=$I+1
                continue
        fi

        CONTENT=$( echo "$OUT" )
        if [[ $CONTENT = $VALUE ]] ; then
                echo "Replacing $CONTENT handler with $HANDLER"
                $BUDDY -c "Delete 'LSHandlers:$I'" $PLIST
                create_entry
                exit
        else
                I=$I+1 
        fi
done
Daniel Beck
quelle
3
Am einfachsten ist es wahrscheinlich, x=~/Library/Preferences/com.apple.LaunchServices.plist; plutil -convert xml1 $x; open -a TextEdit $xdiese LSHandlers-Einträge zu kopieren und einzufügen. Um die Bundle-ID zu erhalten, können Sie Folgendes tun osascript -e 'bundle identifier of (info for (path to app "TextEdit"))'.
Lri
@Lri In gewisser Weise ja, aber diese Frage bezieht sich speziell auf die Befehlszeile. Ich stellte fest, dass TextEdit (oder Property List Editor / Xcode) nicht geeignet ist. Ich habe gerade diesen Teil mit dem Eigenschaftenlisten-Editor aus meiner anderen Antwort zu Illustrationszwecken kopiert. Nützliche Anmerkung zur Bündelkennung.
Daniel Beck
Wenn es nicht einen Alternativen Eintrag für die UTI vorhanden ist , würde zustimmen, dass „Befehlszeile Entfernen eines einzelnen Wörterbuch aus einem Array unnötig schwierig sein kann“?
Graham Perrin
1
@ Abraham Perrin Es ist unnötig schwierig, weil defaultses nicht in der Lage zu sein scheint, und es erfordert ein paar PlistBuddyAnrufe. Es ist jedoch möglich, dies in einem wiederverwendbaren Shell-Skript zu tun.
Daniel Beck