Setting the default Browser on OSX with Ruby

To combat my ADD I want to seperate my work and private browsing. So having two seperate workspaces sounds like a good idea.

I tried Virtue Desktop (and all the other ones) but they were useless to me, because all the virtual desktops show all running applications when switching application with Command+tab. I only want to see the ones in my current desktop.

Creating another user account isn’t an option either because I want to access my mail for both work and private use.

So I need a browser switcher I can run from the commandline so I can schedule it with crontab.

The Objective C part

For the Objecive C part I create a SwitchBrowser directory. In it I create a file called ~/SwitchBrowser/SwitchBrowser.h:

#import <Cocoa/Cocoa.h>

@interface SwitchBrowser : NSObject
{}
- (CFArrayRef) browsers;
- (void)setDefaultBrowser: (CFStringRef) newDefaultStr;
@end

... and a file called ~/SwitchBrowser/SwitchBrowser.m: (Copied from Giant Mike’s FavBrowse)

#import "SwitchBrowser.h" 

@implementation SwitchBrowser

- (CFArrayRef) browsers {
    return LSCopyAllHandlersForURLScheme(CFSTR("https"));
}

- (void)setDefaultBrowser: (CFStringRef) newDefaultStr
{

    //Set the launch services settings for https:// and http://
    LSSetDefaultHandlerForURLScheme(CFSTR("https"), newDefaultStr);
    LSSetDefaultHandlerForURLScheme(CFSTR("http"), newDefaultStr);

    //Set the launch services setting for web sites discovered via Bonjour
    LSSetDefaultRoleHandlerForContentType(CFSTR("public.html"), kLSRolesAll, newDefaultStr);

    FSRef newDefaultBrowserFSRef;
    LSFindApplicationForInfo(kLSUnknownCreator, newDefaultStr, NULL, &newDefaultBrowserFSRef, NULL);
    _LSSetWeakBindingForType(kLSUnknownType, kLSUnknownCreator, CFSTR("xhtm"), kLSRolesAll, &newDefaultBrowserFSRef);
}

@end

void Init_switch_browser(){}

In the SwitchBrowser directory everything is compiled with the following command:

gcc -o switch_browser.bundle -bundle -framework Foundation -framework ApplicationServices -framework AppKit SwitchBrowser.m

The RubyCocoa Part

I use RubyCocoa for the scripting part. After installing it, create a file called ~/switch_browser.rb:

#!/usr/bin/env ruby

require 'osx/cocoa'
require File.dirname(__FILE__) + '/SwitchBrowser/switch_browser'

new_browser = $*[0]

OSX.ns_import :SwitchBrowser
switcher = OSX::SwitchBrowser.alloc.init
browsers = switcher.browsers.collect{|b| b }

unless new_browser
  puts "Select browser number:" 
  browsers.each_with_index{|b,i| puts "#{i} #{b}"}
  new_browser = browsers[gets.chomp!.to_i]
end

raise "#{new_browser} is not a valid browser." unless browsers.include? new_browser

switcher.setDefaultBrowser(new_browser)
puts "Switched to " + new_browser

Now you can do:

~/switch_browser.rb org.mozilla.firefox

I’ve added this to my crontab together with quiting my work applications on the end of my workday. It’s been a real improvement!

admin