Skip to main content
Glama

mcp-google-sheets

create-project.ts7.43 kB
import { createAction, Property } from '@activepieces/pieces-framework'; import { httpClient, HttpMethod } from '@activepieces/pieces-common'; import { fetchUserGroups, fetchUsers, fetchCustomFields, WEALTHBOX_API_BASE, handleApiError, DOCUMENT_TYPES } from '../common'; export const createProject = createAction({ name: 'create_project', displayName: 'Create Project', description: 'Starts a new project with description and organizer. Launch project-based onboarding when new clients sign up.', props: { name: Property.ShortText({ displayName: 'Project Name', description: 'The name of the project (e.g., "Client Onboarding", "Q1 Review Process")', required: true }), description: Property.LongText({ displayName: 'Project Description', description: 'A detailed explanation of the project goals and scope', required: true }), organizer: Property.Dropdown({ displayName: 'Organizer', description: 'Select the user who will be responsible for organizing this project', required: false, refreshers: [], options: async ({ auth }) => { if (!auth) return { options: [] }; try { const users = await fetchUsers(auth as string); const assignableUsers = users.filter((user: any) => !user.excluded_from_assignments); return { options: assignableUsers.map((user: any) => ({ label: `${user.name} (${user.email})`, value: user.id })) }; } catch (error) { return { options: [], error: 'Failed to load users. Please check your authentication.' }; } } }), visible_to: Property.Dropdown({ displayName: 'Visible To', description: 'Select who can view this project', required: false, refreshers: [], options: async ({ auth }) => { if (!auth) return { options: [] }; try { const userGroups = await fetchUserGroups(auth as string); return { options: userGroups.map((group: any) => ({ label: group.name, value: group.name })) }; } catch (error) { return { options: [], error: 'Failed to load user groups. Please check your authentication.' }; } } }), custom_fields: Property.DynamicProperties({ displayName: 'Custom Fields', description: 'Add custom fields to this project', required: false, refreshers: [], props: async ({ auth }) => { if (!auth) { return { custom_fields_array: Property.Array({ displayName: 'Custom Fields', description: 'Add custom fields to this project', required: false, properties: { custom_field: Property.ShortText({ displayName: 'Custom Field', description: 'Custom field name', required: true }), value: Property.ShortText({ displayName: 'Value', description: 'The value for this custom field', required: true }) } }) }; } try { const customFields = await fetchCustomFields(auth as unknown as string, DOCUMENT_TYPES.PROJECT); const customFieldOptions = customFields.map((field: any) => ({ label: field.name, value: field.name })); return { custom_fields_array: Property.Array({ displayName: 'Custom Fields', description: 'Add custom fields to this project', required: false, properties: { custom_field: Property.StaticDropdown({ displayName: 'Custom Field', description: 'Select a custom field for this project', required: true, options: { options: customFieldOptions } }), value: Property.ShortText({ displayName: 'Value', description: 'The value for this custom field', required: true }) } }) }; } catch (error) { return { custom_fields_array: Property.Array({ displayName: 'Custom Fields', description: 'Add custom fields to this project (API unavailable)', required: false, properties: { custom_field: Property.ShortText({ displayName: 'Custom Field Name', description: 'Enter the custom field name exactly', required: true }), value: Property.ShortText({ displayName: 'Value', description: 'The value for this custom field', required: true }) } }) }; } } }) }, async run(context) { const { auth, propsValue } = context; if (!auth) { throw new Error('Authentication is required'); } const requestBody: any = { name: propsValue.name, description: propsValue.description }; if (propsValue.organizer) { requestBody.organizer = propsValue.organizer; } if (propsValue.visible_to) { requestBody.visible_to = propsValue.visible_to; } const customFieldsArray = (propsValue as any).custom_fields_array; if (customFieldsArray && Array.isArray(customFieldsArray) && customFieldsArray.length > 0) { try { const customFields = await fetchCustomFields(auth as unknown as string, DOCUMENT_TYPES.PROJECT); const customFieldMap = new Map(customFields.map((field: any) => [field.name, field.id])); requestBody.custom_fields = customFieldsArray.map((field: any) => { const fieldId = customFieldMap.get(field.custom_field); if (!fieldId) { throw new Error(`Custom field "${field.custom_field}" not found. Please check the field name.`); } return { id: fieldId, value: field.value }; }); } catch (error) { if (error instanceof Error && error.message.includes('Custom field')) { throw error; } console.warn('Could not fetch custom fields for validation:', error); requestBody.custom_fields = customFieldsArray.map((field: any) => ({ id: field.custom_field, value: field.value })); } } try { const response = await httpClient.sendRequest({ method: HttpMethod.POST, url: `${WEALTHBOX_API_BASE}/projects`, headers: { 'ACCESS_TOKEN': auth as string, 'Content-Type': 'application/json' }, body: requestBody }); if (response.status >= 400) { handleApiError('create project', response.status, response.body); } return response.body; } catch (error) { throw new Error(`Failed to create project: ${error instanceof Error ? error.message : 'Unknown error'}`); } } });

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