Skip to main content
Glama

mcp-google-sheets

search-invoices.ts15.1 kB
import { createAction, Property } from '@activepieces/pieces-framework'; import { HttpMethod } from '@activepieces/pieces-common'; import { teamleaderAuth } from '../common/auth'; import { teamleaderCommon } from '../common/client'; export const searchInvoices = createAction({ name: 'search_invoices', displayName: 'Search Invoices', description: 'List or filter invoices', auth: teamleaderAuth, props: { term: Property.ShortText({ displayName: 'Search Term', description: 'Search by invoice number, purchase order number, payment reference or customer name', required: false, }), invoice_number: Property.ShortText({ displayName: 'Invoice Number', description: 'Filter by full invoice number (e.g., "2017 / 5")', required: false, }), customer_type: Property.StaticDropdown({ displayName: 'Customer Type', description: 'Type of customer to filter by', required: false, options: { options: [ { label: 'Company', value: 'company' }, { label: 'Contact', value: 'contact' } ] } }), customer_id: Property.Dropdown({ displayName: 'Customer', description: 'Filter invoices by specific customer', required: false, refreshers: ['customer_type'], options: async ({ auth, customer_type }) => { if (!auth) return { disabled: true, options: [], placeholder: 'Please authenticate first' }; if (!customer_type) return { disabled: true, options: [], placeholder: 'Please select customer type first' }; try { if (customer_type === 'company') { const response = await teamleaderCommon.apiCall({ auth: auth as any, method: HttpMethod.POST, resourceUri: '/companies.list', body: {} }); return { disabled: false, options: response.body.data.map((company: any) => ({ label: company.name, value: company.id })) }; } else { const response = await teamleaderCommon.apiCall({ auth: auth as any, method: HttpMethod.POST, resourceUri: '/contacts.list', body: {} }); return { disabled: false, options: response.body.data.map((contact: any) => ({ label: `${contact.first_name} ${contact.last_name || ''}`.trim(), value: contact.id })) }; } } catch (error) { return { disabled: true, options: [], placeholder: 'Error loading customers' }; } } }), department_id: Property.Dropdown({ displayName: 'Department', description: 'Filter by department (company entity)', required: false, refreshers: [], options: async ({ auth }) => { if (!auth) return { disabled: true, options: [], placeholder: 'Please authenticate first' }; try { const response = await teamleaderCommon.apiCall({ auth: auth as any, method: HttpMethod.POST, resourceUri: '/departments.list', body: { filter: { status: ['active'] } } }); return { disabled: false, options: response.body.data.map((department: any) => ({ label: department.name, value: department.id })) }; } catch (error) { return { disabled: true, options: [], placeholder: 'Error loading departments' }; } } }), deal_id: Property.Dropdown({ displayName: 'Deal', description: 'Filter by associated deal', required: false, refreshers: [], options: async ({ auth }) => { if (!auth) return { disabled: true, options: [], placeholder: 'Please authenticate first' }; try { const response = await teamleaderCommon.apiCall({ auth: auth as any, method: HttpMethod.POST, resourceUri: '/deals.list', body: {} }); return { disabled: false, options: response.body.data.map((deal: any) => ({ label: deal.title, value: deal.id })) }; } catch (error) { return { disabled: true, options: [], placeholder: 'Error loading deals' }; } } }), project_id: Property.Dropdown({ displayName: 'Project', description: 'Filter by associated project', required: false, refreshers: [], options: async ({ auth }) => { if (!auth) return { disabled: true, options: [], placeholder: 'Please authenticate first' }; try { const response = await teamleaderCommon.apiCall({ auth: auth as any, method: HttpMethod.POST, resourceUri: '/projects.list', body: {} }); return { disabled: false, options: response.body.data.map((project: any) => ({ label: project.title, value: project.id })) }; } catch (error) { return { disabled: true, options: [], placeholder: 'Error loading projects' }; } } }), subscription_id: Property.Dropdown({ displayName: 'Subscription', description: 'Filter by associated subscription', required: false, refreshers: [], options: async ({ auth }) => { if (!auth) return { disabled: true, options: [], placeholder: 'Please authenticate first' }; try { const response = await teamleaderCommon.apiCall({ auth: auth as any, method: HttpMethod.POST, resourceUri: '/subscriptions.list', body: {} }); return { disabled: false, options: response.body.data.map((subscription: any) => ({ label: subscription.title || subscription.reference, value: subscription.id })) }; } catch (error) { return { disabled: true, options: [], placeholder: 'Error loading subscriptions' }; } } }), status: Property.StaticMultiSelectDropdown({ displayName: 'Status', description: 'Filter by invoice status (multiple selection)', required: false, options: { options: [ { label: 'Draft', value: 'draft' }, { label: 'Outstanding', value: 'outstanding' }, { label: 'Matched', value: 'matched' } ] } }), purchase_order_number: Property.ShortText({ displayName: 'Purchase Order Number', description: 'Filter by purchase order number', required: false, }), payment_reference: Property.ShortText({ displayName: 'Payment Reference', description: 'Filter by payment reference', required: false, }), invoice_date_after: Property.DateTime({ displayName: 'Invoice Date After', description: 'Filter invoices with date after this date (inclusive)', required: false, }), invoice_date_before: Property.DateTime({ displayName: 'Invoice Date Before', description: 'Filter invoices with date before this date (inclusive)', required: false, }), updated_since: Property.DateTime({ displayName: 'Updated Since', description: 'Only invoices updated after this date', required: false, }), sort_field: Property.StaticDropdown({ displayName: 'Sort Field', description: 'Field to sort by', required: false, options: { options: [ { label: 'Invoice Number', value: 'invoice_number' }, { label: 'Invoice Date', value: 'invoice_date' } ] } }), sort_order: Property.StaticDropdown({ displayName: 'Sort Order', description: 'Sort direction', required: false, options: { options: [ { label: 'Ascending', value: 'asc' }, { label: 'Descending', value: 'desc' } ] } }), page_size: Property.Number({ displayName: 'Results Per Page', description: 'Number of results per page (default: 20)', required: false, }), page_number: Property.Number({ displayName: 'Page Number', description: 'Page number to retrieve (default: 1)', required: false, }), include_late_fees: Property.Checkbox({ displayName: 'Include Late Fee Information', description: 'Include late fee and interest calculations in response', required: false, }), }, async run(context) { const requestBody: Record<string, any> = {}; const filter: Record<string, any> = {}; if (context.propsValue.term) { filter['term'] = context.propsValue.term; } if (context.propsValue.invoice_number) { filter['invoice_number'] = context.propsValue.invoice_number; } if (context.propsValue.customer_type && context.propsValue.customer_id) { filter['customer'] = { type: context.propsValue.customer_type, id: context.propsValue.customer_id }; } if (context.propsValue.department_id) { filter['department_id'] = context.propsValue.department_id; } if (context.propsValue.deal_id) { filter['deal_id'] = context.propsValue.deal_id; } if (context.propsValue.project_id) { filter['project_id'] = context.propsValue.project_id; } if (context.propsValue.subscription_id) { filter['subscription_id'] = context.propsValue.subscription_id; } if (context.propsValue.status && context.propsValue.status.length > 0) { filter['status'] = context.propsValue.status; } if (context.propsValue.purchase_order_number) { filter['purchase_order_number'] = context.propsValue.purchase_order_number; } if (context.propsValue.payment_reference) { filter['payment_reference'] = context.propsValue.payment_reference; } if (context.propsValue.invoice_date_after) { const afterDate = new Date(context.propsValue.invoice_date_after); filter['invoice_date_after'] = afterDate.toISOString().split('T')[0]; } if (context.propsValue.invoice_date_before) { const beforeDate = new Date(context.propsValue.invoice_date_before); filter['invoice_date_before'] = beforeDate.toISOString().split('T')[0]; } if (context.propsValue.updated_since) { const updatedSince = new Date(context.propsValue.updated_since); filter['updated_since'] = updatedSince.toISOString(); } if (Object.keys(filter).length > 0) { requestBody['filter'] = filter; } const page: Record<string, number> = {}; if (context.propsValue.page_size) { page['size'] = context.propsValue.page_size; } if (context.propsValue.page_number) { page['number'] = context.propsValue.page_number; } if (Object.keys(page).length > 0) { requestBody['page'] = page; } if (context.propsValue.sort_field && context.propsValue.sort_order) { requestBody['sort'] = [{ field: context.propsValue.sort_field, order: context.propsValue.sort_order }]; } if (context.propsValue.include_late_fees) { requestBody['includes'] = 'late_fees'; } const response = await teamleaderCommon.apiCall({ auth: context.auth, method: HttpMethod.POST, resourceUri: '/invoices.list', body: requestBody }); return response.body; }, });

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/activepieces/activepieces'

If you have feedback or need assistance with the MCP directory API, please join our Discord server