Skip to content

Instantly share code, notes, and snippets.

@stephancasas
Last active December 3, 2024 10:28
Show Gist options
  • Save stephancasas/14661a231f9763c253afd288b1046586 to your computer and use it in GitHub Desktop.
Save stephancasas/14661a231f9763c253afd288b1046586 to your computer and use it in GitHub Desktop.
AppleScript: Bulk-rename export EML messages
#!/usr/bin/env osascript -l JavaScript
const App = Application.currentApplication();
App.includeStandardAdditions = true;
function run(_) {
// Prompt for folder selection.
const dir = `${App.chooseFolder({
withPrompt: 'Select the folder containing your exported messages...',
})}`;
// Read content of directory into list.
const messages = App.doShellScript(`ls '${dir}'`).split('\r');
messages.forEach((path) => {
path = `${dir}/${path}`;
// Skip if path does not end in `.eml`.
if ([...path].slice(-4).join('') != '.eml') {
return;
}
// Read message content to string.
const content = $.NSString.stringWithContentsOfFileEncodingError(
path,
$.NSUTF8StringEncoding,
$(),
).js;
// Skip if file was unreadable.
if (typeof content == 'undefined') {
return;
}
// Extract parts for renaming...
const { subject } = content.match(/(^Subject:\s?(?<subject>.+))/im).groups;
let { sender } = content.match(/(^From:\s?(?<sender>.+))/im).groups;
if ((senderAddress = sender.match(/\<[^@]+@[^\>]+\>/))) {
sender = senderAddress[0].replace(/(\<|\>)/g, '');
}
let { timestamp } = content.match(/(^Date:\s?(?<timestamp>.+))/im).groups;
// Skip if unable to extract all parts...
if (!subject || !sender || !timestamp) {
return;
}
// Reformat date to desired format...
timestamp = new Date(timestamp);
const year = timestamp.getFullYear().toString();
const month = (timestamp.getMonth() + 1).toString().padStart(2, '0');
const day = timestamp.getDate().toString().padStart(2, '0');
const hours = timestamp.getHours().toString().padStart(2, '0');
const minutes = timestamp.getMinutes().toString().padStart(2, '0');
const seconds = timestamp.getSeconds().toString().padStart(2, '0');
timestamp = year + month + day + '_' + hours + minutes + seconds;
// Perform rename operation.
const basename = `[${timestamp}][${sender}] ${subject}`.trim().replace(/[\/\?<>\\:\*\'|"]/g, '_');
App.doShellScript(
`mv '${path}' '${dir}/${basename}.eml'`,
);
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment