Snippets · 12 functions
Gmail snippets
Twelve short functions for the Gmail tasks that come up again and again: searching, reading, sending, and labeling.
How to use these
Set up before you run
Copy a snippet into a script file, read its setup and notes, change the placeholder values, and save. For functions meant to run manually, choose the function name in the toolbar and press Run. Results appear in the Execution log unless the description says otherwise.
1
Search threads with a query
Run a Gmail search, the same kind you type in the Gmail search box, and get back a list of matching threads.
function searchRecentThreadsFromSender() {
const query = 'from:billing@example.com newer_than:7d';
const threads = GmailApp.search(query);
Logger.log('Found ' + threads.length + ' threads.');
} 2
Read sender, subject, and date of the newest message in a thread
Look at the most recent message in a thread to see who sent it, what it says in the subject line, and when it arrived.
function logNewestMessageDetails() {
const threads = GmailApp.search('from:billing@example.com');
if (!threads.length) return;
const messages = threads[0].getMessages();
const newest = messages[messages.length - 1];
Logger.log(newest.getFrom() + ' | ' + newest.getSubject() + ' | ' + newest.getDate());
} 3
Send a plain-text email
Send a plain email with a subject and body.
function sendPlainTextEmail() {
const recipient = 'you@example.com';
const subject = 'A quick update';
const body = 'This is a plain-text message sent from Apps Script.';
GmailApp.sendEmail(recipient, subject, body);
Logger.log('Sent to ' + recipient);
} 4
Send an HTML email with htmlBody
Send a formatted email by passing an htmlBody option, while keeping a plain-text body as a fallback.
function sendHtmlEmail() {
const recipient = 'you@example.com';
const subject = 'A formatted update';
const plainBody = 'This message needs an HTML-capable email client.';
const htmlBody = '<p>This is <strong>bold</strong> and this is <em>italic</em>.</p>';
GmailApp.sendEmail(recipient, subject, plainBody, { htmlBody: htmlBody });
Logger.log('Sent HTML email to ' + recipient);
} Good to know. Always include a plain-text body too, in case the recipient's email client cannot show HTML.
5
Send with an attachment from Drive
Attach an existing Drive file to an email by turning it into a blob first.
function sendEmailWithDriveAttachment() {
const fileId = 'REPLACE_WITH_FILE_ID';
const file = DriveApp.getFileById(fileId);
const recipient = 'you@example.com';
GmailApp.sendEmail(recipient, 'A file for you', 'See the attached file.', {
attachments: [file.getBlob()]
});
Logger.log('Sent ' + file.getName() + ' to ' + recipient);
} 6
Create a draft instead of sending
Save a message as a draft so a person can review and send it themselves, instead of the script sending it right away.
GmailApp.GmailDraftfunction createFollowUpDraft() {
const recipient = 'you@example.com';
const subject = 'Draft for review';
const body = 'This draft was created by a script and is waiting for review.';
const draft = GmailApp.createDraft(recipient, subject, body);
Logger.log('Draft created with id ' + draft.getId());
} 7
Add a label to matching threads
Search for threads and tag every result with an existing Gmail label so they are easy to find later.
function labelInvoiceThreads() {
const label = GmailApp.getUserLabelByName('Invoices');
if (!label) throw new Error('Create a Gmail label named Invoices before running this function.');
const threads = GmailApp.search('subject:invoice newer_than:30d');
threads.forEach((thread) => label.addToThread(thread));
Logger.log('Labeled ' + threads.length + ' threads.');
} 8
Mark a thread as read
Clear the unread status on the first matching thread, the same effect as opening it in Gmail.
function markFirstMatchingThreadRead() {
const threads = GmailApp.search('from:billing@example.com is:unread');
if (!threads.length) return;
threads[0].markRead();
Logger.log('Marked thread as read.');
} 9
Star a message
Add a star to the newest message in a thread so it stands out in the Gmail inbox.
function starNewestMatchingMessage() {
const threads = GmailApp.search('from:billing@example.com');
if (!threads.length) return;
const messages = threads[0].getMessages();
const newest = messages[messages.length - 1];
GmailApp.starMessage(newest);
Logger.log('Starred message from ' + newest.getFrom());
} 10
Count unread threads in the inbox
Get a single number for how many inbox threads are currently unread, useful for a daily summary.
function logUnreadInboxCount() {
const unreadCount = GmailApp.getInboxUnreadCount();
Logger.log('Unread threads in inbox: ' + unreadCount);
} 11
Get the plain body of a message
Read the plain-text body of the newest message in a thread, without any HTML formatting.
function logNewestMessageBody() {
const threads = GmailApp.search('from:billing@example.com');
if (!threads.length) return;
const messages = threads[0].getMessages();
const newest = messages[messages.length - 1];
Logger.log(newest.getPlainBody());
} 12
List your labels
Get every Gmail label you have created so a script can check which ones already exist.
function logAllLabelNames() {
const labels = GmailApp.getUserLabels();
const names = labels.map((label) => label.getName());
Logger.log(names);
} Keep going
See these in a complete task
- Task guide Send an email for each row in a Google Sheet
Use one row per person, then let the script send only the rows that have not already been marked as sent.
- Task guide Label emails from one sender in Gmail
Search your mailbox with GmailApp.search() for messages from one sender address, then call thread.addLabel() so those conversations are easy to find later.
- Task guide Log new emails to a Google Sheet
Search your recent mail and add one row per message to a tab named Email log. A hidden ID column keeps a second run from adding the same message twice.
- Task guide Save labeled Gmail attachments to Drive
Choose the email threads yourself by adding a Gmail label, then copy their attachments into an existing Drive folder.
- Basics Apps Script permissions and authorization
Before a script can read your sheet or send your mail, you give it permission to access a list of OAuth scopes. This page walks through each authorization screen, explains @OnlyCurrentDoc, and shows how to revoke access.
- Basics Google Apps Script quotas and limits
Google caps how long one run may take and how much your scripts may do in a day. Knowing the caps changes how you write anything that touches a lot of rows.