MacOS equivalent of the Windows assoc command

applescriptautomatorbashdefaultsterminal

I am looking to change a file association on the Mac using some sort of script. I know that I can do something like that in Windows using the assoc command.

Is there something scriptable on macOS which will do a similar job? I don’t mind whether it’s in Bash (my preference), AppleScript or something in Automator.

I am aware of the dutil command but I want to be able to do it without additional software.

Best Answer

Changing the file association for a single file or a set of files (AppleScript)

This script demonstrates first that the default application for some text file on my system was set to TextEdit. Then it changes the file association for that particular file so it now opens with Atom. Finally, it associates all text files on the desktop with the Atom application.

tell application "System Events"
    get the default application of the file "/path/to/some file.txt"
        --> alias "Macintosh HD:Applications:TextEdit.app:" of application "System Events"

    # Individual file:
    set the default application of the file "/path/to/some file.txt" to ¬
        the path to the application named "Atom"

    # A set of files:
    set the default application of every file of the desktop folder whose ¬
        name extension = "txt" to the path to the application "Atom"
end tell

Changing the file associations for all files of a given type (JXA)

Using JavaScript for Automation, you can implement Core Foundation functions in a way you cannot do with AppleScriptObjC, so as to interact with Launch Services at the system level and change the file association for a given file type.

Here, I've targetted plain text files (these have extension .txt by default), and switched the default application that responds to them to Atom:

ObjC.import('CoreServices');

var contentType = 'public.plain-text';
var bundleID = Application('Atom').id();

$.LSSetDefaultRoleHandlerForContentType(
            contentType, 
            $.kLSRolesAll, 
            bundleID
        );

The file type must be targeted by way of a Uniform Type Identifier. These are special text strings that uniquely identify a given class or type of item. The link will take you to a page that lists Apple's system-declared UTIs for all the likely file types that you'll be interested in. Be careful not to simply choose the one that appears to match your needs at first glance, as UTIs are structured in a kind of inheritance tree. Therefore, I could have lazily picked out public.text, which I saw first in the list, until on further reading, we learn that this UTI is a base type for all text, which would include HTML and RTF files.