UNPKG

n8n-nodes-imap-ai

Version:

Simplified IMAP node for n8n with AI-agent support. Clean and modular email and mailbox management for automation workflows.

296 lines 11.8 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.SearchEmailsOperation = void 0; const n8n_workflow_1 = require("n8n-workflow"); const helpers_1 = require("../utils/helpers"); class SearchEmailsOperation { async execute(executeFunctions, client, itemIndex) { const mailboxParam = executeFunctions.getNodeParameter('mailbox', itemIndex); const mailbox = helpers_1.ParameterValidator.extractMailboxName(mailboxParam); const limit = executeFunctions.getNodeParameter('limit', itemIndex); const searchMode = executeFunctions.getNodeParameter('searchMode', itemIndex); helpers_1.ParameterValidator.validateMailbox(mailboxParam); const validatedLimit = Math.max(1, Math.min(limit, 1000)); try { await client.mailboxOpen(mailbox); } catch (error) { throw new n8n_workflow_1.NodeApiError(executeFunctions.getNode(), { message: `Failed to open mailbox ${mailbox}: ${error.message}`, }); } let searchCriteria = {}; let searchDisplayText = ''; if (searchMode === 'simple') { const quickFilter = executeFunctions.getNodeParameter('quickFilter', itemIndex); const simpleSearchText = executeFunctions.getNodeParameter('simpleSearchText', itemIndex); searchCriteria = this.buildSimpleSearchCriteria(quickFilter, simpleSearchText); searchDisplayText = this.buildSimpleSearchDisplay(quickFilter, simpleSearchText); } else { const advancedCriteria = executeFunctions.getNodeParameter('advancedCriteria', itemIndex); const result = this.buildAdvancedSearchCriteria(advancedCriteria); searchCriteria = result.criteria; searchDisplayText = result.display; } console.log('Search criteria:', JSON.stringify(searchCriteria, null, 2)); console.log('Search display:', searchDisplayText); let searchResults = []; try { searchResults = await client.search(searchCriteria, { uid: true }); } catch (error) { throw new n8n_workflow_1.NodeApiError(executeFunctions.getNode(), { message: `Server-side search failed: ${error.message}. Query: ${searchDisplayText}`, }); } console.log(`Server-side search completed. Found ${searchResults.length} UIDs matching criteria`); if (searchResults.length === 0) { return [ { json: { searchSummary: { totalFound: 0, returned: 0, query: searchDisplayText, criteria: searchCriteria, folder: mailbox, }, uids: [], firstUID: null, }, }, ]; } const sortedResults = searchResults.sort((a, b) => b - a); const limitedResults = sortedResults.slice(0, validatedLimit); console.log(`Validating ${limitedResults.length} UIDs from server-side search...`); let validUIDs = []; try { for (const uid of limitedResults) { const exists = await client.search({ uid: uid.toString() }); if (exists.length > 0) { validUIDs.push(uid); console.log(`UID ${uid} exists and is valid`); } else { console.log(`UID ${uid} no longer exists, skipping`); } if (validUIDs.length >= validatedLimit) break; } console.log(`Found ${validUIDs.length} valid UIDs from ${limitedResults.length} search results`); } catch (error) { console.error('UID validation failed:', error); throw new n8n_workflow_1.NodeApiError(executeFunctions.getNode(), { message: `Failed to validate email UIDs: ${error.message}`, }); } if (validUIDs.length === 0) { return [ { json: { searchSummary: { totalFound: searchResults.length, returned: 0, query: searchDisplayText, criteria: searchCriteria, folder: mailbox, note: "Search found emails but none exist in current mailbox state", }, uids: [], firstUID: null, }, }, ]; } const result = { json: { searchSummary: { totalFound: searchResults.length, returned: validUIDs.length, query: searchDisplayText, criteria: searchCriteria, folder: mailbox, }, uids: validUIDs, firstUID: validUIDs.length > 0 ? validUIDs[0] : null, }, }; return [result]; } buildSimpleSearchCriteria(quickFilter, searchText) { const criteria = {}; switch (quickFilter) { case 'unseen': criteria.unseen = true; break; case 'seen': criteria.seen = true; break; case 'today': criteria.since = new Date(new Date().setHours(0, 0, 0, 0)); break; case 'thisWeek': const weekStart = new Date(); weekStart.setDate(weekStart.getDate() - weekStart.getDay()); weekStart.setHours(0, 0, 0, 0); criteria.since = weekStart; break; case 'thisMonth': const monthStart = new Date(); monthStart.setDate(1); monthStart.setHours(0, 0, 0, 0); criteria.since = monthStart; break; case 'flagged': criteria.flagged = true; break; case 'all': default: break; } if (searchText && searchText.trim()) { const text = searchText.trim(); if (text.includes('@')) { criteria.or = [ { from: text }, { to: text }, { cc: text }, ]; } else { criteria.or = [ { subject: text }, { from: text }, { body: text }, ]; } } return criteria; } buildSimpleSearchDisplay(quickFilter, searchText) { const parts = []; switch (quickFilter) { case 'unseen': parts.push('unread emails'); break; case 'seen': parts.push('read emails'); break; case 'today': parts.push('emails from today'); break; case 'thisWeek': parts.push('emails from this week'); break; case 'thisMonth': parts.push('emails from this month'); break; case 'flagged': parts.push('flagged emails'); break; case 'all': default: parts.push('all emails'); break; } if (searchText && searchText.trim()) { if (searchText.includes('@')) { parts.push(`from/to: ${searchText}`); } else { parts.push(`containing: ${searchText}`); } } return parts.join(' '); } buildAdvancedSearchCriteria(advancedCriteria) { const criteria = {}; const displayParts = []; if (advancedCriteria.subject) { criteria.subject = advancedCriteria.subject; displayParts.push(`subject: ${advancedCriteria.subject}`); } if (advancedCriteria.from) { criteria.from = advancedCriteria.from; displayParts.push(`from: ${advancedCriteria.from}`); } if (advancedCriteria.to) { criteria.to = advancedCriteria.to; displayParts.push(`to: ${advancedCriteria.to}`); } if (advancedCriteria.body) { criteria.body = advancedCriteria.body; displayParts.push(`body: ${advancedCriteria.body}`); } if (advancedCriteria.seen !== undefined) { if (advancedCriteria.seen) { criteria.seen = true; displayParts.push('read'); } else { criteria.unseen = true; displayParts.push('unread'); } } if (advancedCriteria.flagged) { criteria.flagged = true; displayParts.push('flagged'); } this.applyDateFilters(criteria, advancedCriteria, displayParts); return { criteria, display: displayParts.length > 0 ? displayParts.join(', ') : 'all emails', }; } applyDateFilters(criteria, advancedCriteria, displayParts) { if (advancedCriteria.quickDate && advancedCriteria.quickDate !== 'none') { const dateRange = this.getQuickDateRange(advancedCriteria.quickDate); Object.assign(criteria, dateRange); displayParts.push(`date: ${advancedCriteria.quickDate}`); } if (advancedCriteria.dateFrom) { criteria.since = new Date(advancedCriteria.dateFrom); displayParts.push(`since: ${advancedCriteria.dateFrom}`); } if (advancedCriteria.dateTo) { criteria.before = new Date(advancedCriteria.dateTo); displayParts.push(`before: ${advancedCriteria.dateTo}`); } } getQuickDateRange(quickDate) { const now = new Date(); const today = new Date(now.getFullYear(), now.getMonth(), now.getDate()); switch (quickDate) { case 'today': return { since: today }; case 'yesterday': const yesterday = new Date(today); yesterday.setDate(yesterday.getDate() - 1); return { since: yesterday, before: today }; case 'thisWeek': const weekStart = new Date(today); weekStart.setDate(today.getDate() - today.getDay()); return { since: weekStart }; case 'lastWeek': const lastWeekEnd = new Date(today); lastWeekEnd.setDate(today.getDate() - today.getDay()); const lastWeekStart = new Date(lastWeekEnd); lastWeekStart.setDate(lastWeekEnd.getDate() - 7); return { since: lastWeekStart, before: lastWeekEnd }; case 'thisMonth': const monthStart = new Date(today.getFullYear(), today.getMonth(), 1); return { since: monthStart }; case 'lastMonth': const lastMonthStart = new Date(today.getFullYear(), today.getMonth() - 1, 1); const lastMonthEnd = new Date(today.getFullYear(), today.getMonth(), 1); return { since: lastMonthStart, before: lastMonthEnd }; default: return {}; } } } exports.SearchEmailsOperation = SearchEmailsOperation; //# sourceMappingURL=searchEmails.js.map