Files
sim/apps/sim/tools/gmail/send.ts
Waleed Latif ff2b1d33c8 fix(tool-input): added tool input, visibility enum for tool params, fixed google provider bugs (#674)
* transfrom from block-centric tool input component to tool-centric tool input component for agent tools

* added additional type safety, created generic wrapper for tool input & reused across all subblock types

* stop retries if tool call fails, implemented for all providers except google

* bug fix with tool name extraction

* another bug fix

* ran script to update docs

* update contributing guide tool/block add example to reflect new param structure

* update README

* add key control to combobox, fixed google

* fixed google provider, fixed combobox

* fixed a ton of tools, ensured that the agent tool has full parity with actual tool for all tools

* update docs to reflect new structure

* updated visibility for gmail draft

* standardize dropdown values for tool definitions

* add asterisk for user-only + required fields

* updated visibility for tools

* consolidate redactApiKey util, fixed console entry bug that overwrites previous block logs

* updated docs

* update contributing guide to guide users to point their branches at staging instead of main

* nits

* move socket tests
2025-07-13 20:16:49 -07:00

101 lines
2.5 KiB
TypeScript

import type { ToolConfig } from '../types'
import type { GmailSendParams, GmailToolResponse } from './types'
const GMAIL_API_BASE = 'https://gmail.googleapis.com/gmail/v1/users/me'
export const gmailSendTool: ToolConfig<GmailSendParams, GmailToolResponse> = {
id: 'gmail_send',
name: 'Gmail Send',
description: 'Send emails using Gmail',
version: '1.0.0',
oauth: {
required: true,
provider: 'google-email',
additionalScopes: ['https://www.googleapis.com/auth/gmail.send'],
},
params: {
accessToken: {
type: 'string',
required: true,
visibility: 'hidden',
description: 'Access token for Gmail API',
},
to: {
type: 'string',
required: true,
visibility: 'user-or-llm',
description: 'Recipient email address',
},
subject: {
type: 'string',
required: true,
visibility: 'user-or-llm',
description: 'Email subject',
},
body: {
type: 'string',
required: true,
visibility: 'user-or-llm',
description: 'Email body content',
},
},
request: {
url: () => `${GMAIL_API_BASE}/messages/send`,
method: 'POST',
headers: (params: GmailSendParams) => ({
Authorization: `Bearer ${params.accessToken}`,
'Content-Type': 'application/json',
}),
body: (params: GmailSendParams): Record<string, any> => {
const email = [
'Content-Type: text/plain; charset="UTF-8"',
'MIME-Version: 1.0',
`To: ${params.to}`,
`Subject: ${params.subject}`,
'',
params.body,
].join('\n')
return {
raw: Buffer.from(email).toString('base64url'),
}
},
},
transformResponse: async (response) => {
const data = await response.json()
if (!response.ok) {
throw new Error(data.error?.message || 'Failed to send email')
}
return {
success: true,
output: {
content: 'Email sent successfully',
metadata: {
id: data.id,
threadId: data.threadId,
labelIds: data.labelIds,
},
},
}
},
transformError: (error) => {
if (error.error?.message) {
if (error.error.message.includes('invalid authentication credentials')) {
return 'Invalid or expired access token. Please reauthenticate.'
}
if (error.error.message.includes('quota')) {
return 'Gmail API quota exceeded. Please try again later.'
}
return error.error.message
}
return error.message || 'An unexpected error occurred while sending email'
},
}