Say you have the name of an application, Mail.app
, how do you programmatically obtain com.apple.mail
from the application name?
Asked
Active
Viewed 7,648 times
7

David Kennedy of Zenopolis
- 924
- 8
- 12

Tony
- 36,591
- 10
- 48
- 83
5 Answers
17
The following method will return an application's Bundle Identifier for a named application:
- (NSString *) bundleIdentifierForApplicationName:(NSString *)appName
{
NSWorkspace * workspace = [NSWorkspace sharedWorkspace];
NSString * appPath = [workspace fullPathForApplication:appName];
if (appPath) {
NSBundle * appBundle = [NSBundle bundleWithPath:appPath];
return [appBundle bundleIdentifier];
}
return nil;
}
For Mail you can call the method like so:
NSString * appID = [self bundleIdentifierForApplicationName:@"Mail"];
appID
now contains com.apple.mail
Swift 5.1
import AppKit
func bundleIdentifier(forAppName appName: String) -> String? {
let workspace = NSWorkspace.shared
let appPath = workspace.fullPath(forApplication: appName)
if let appPath = appPath {
let appBundle = Bundle(path: appPath)
return appBundle?.bundleIdentifier
}
return nil
}
// For Mail you can call the method like so:
let appID = bundleIdentifier(forAppName: "Mail")
Deprecation
The fullPathForApplication:
/ fullPath(forApplication:)
method has been deprecated in macOS 10.15 - it is unclear what the answer is going forward.

David Kennedy of Zenopolis
- 924
- 8
- 12
-
Thanks! That's exactly what i was looking for. However, in my tests `Mail.app` works as well, which isn't surprising given that apple says `.app` is optional in many of its docs. However, `MAil.app` and `Mail.APP` also seem to work, so I guess perhaps application name isn't exactly case sensitive either. – Tony Feb 25 '12 at 04:34
-
OK I'll remove the note that says otherwise – David Kennedy of Zenopolis Feb 25 '12 at 09:22
-
Note that `fullPathForApplication:appName` is soft-deprecated in macOS 10.15. I couldn't find any alternative, so I guess Apple wants us to only use bundle identifiers... – Sindre Sorhus Jan 31 '20 at 08:06
-
Thank you Sindre Sorhus, I've added a deprivation notice. – David Kennedy of Zenopolis Feb 11 '20 at 10:18
1
Expanding on Francesco Germinara's answer in Swift 4, macOS 10.13.2:
extension Bundle {
class func bundleIDFor(appNamed appName: String) -> String? {
if let appPath = NSWorkspace.shared.fullPath(forApplication: appName) {
if let itsBundle = Bundle(path: appPath) { // < in my build this condition fails if we're looking for the ID of the app we're running...
if let itsID = itsBundle.bundleIdentifier {
return itsID
}
} else {
//Attempt to get the current running app.
//This is probably too simplistic a catch for every single possibility
if let ownID = Bundle.main.bundleIdentifier {
return ownID
}
}
}
return nil
}
}
Placing it your Swift project, you can call it like this:
let id = Bundle.bundleIDFor(appNamed: "Mail.app")
or
let id = Bundle.bundleIDFor(appNamed: "Mail")
0
You can write:
Swift 5
Import AppKit // Not needed if you already import Cocoa or SwiftUI
func bundleIdentifier(forAppName appName: String) -> String? {
NSWorkspace.shared.runningApplications.first(where:
{ $0.bundleURL?.lastPathComponent == appName })?.bundleIdentifier
}
let id = bundleIdentifier(forAppName: "Mail.app")
If you have app names without extension, replace inside the closure with the following code:
$0.bundleURL.localizedName == appName

soundflix
- 928
- 9
- 22
0
It's the value for the key CFBundleIdentifier in Contents/Info.plist

ABS
- 2,092
- 1
- 13
- 6
-
Adding to that, the application's "Contents" folder can be usually found in /Applications/
/ – Ron U Sep 20 '20 at 09:37.app/Contents/
-1
This is a possible swift implementation
func bundleIdentifierForApplicationName(appName : String) -> String
{
var workspace = NSWorkspace.sharedWorkspace()
var appPath : String = workspace.fullPathForApplication(appName)
if (appPath != "") {
var appBundle : NSBundle = NSBundle(path:appPath)
return appBundle.bundleIdentifier
}
return ""
}

Francesco Germinara
- 508
- 5
- 8