import { Client } from "@hubspot/api-client"; import { AssociationSpecAssociationCategoryEnum } from "@hubspot/api-client/lib/codegen/crm/objects/meetings/models/AssociationSpec"; import { PublicAssociationsForObject } from "@hubspot/api-client/lib/codegen/crm/objects/meetings"; import z, { email } from "zod"; const hubspotClient = new Client({ accessToken: process.env.HUBSPOT_ACCESS_TOKEN }); export const CompanySchema = z.object({ id: z.string(), name: z.string(), }); export const OwnerSchema = z.object({ id: z.string(), email: z.string().optional().default(''), }); export type Company = z.infer; export type Owner = z.infer; export const hubspotController = { check: async(): Promise => { try { const response = await hubspotClient.crm.companies.getAll(); console.log(response.length); console.log("HubSpot connection check successful."); return true; } catch (error) { console.error("HubSpot connection check failed:", error); return false; } }, getCompanies: async(): Promise => { try { const allCompanies: Company[] = []; const limit = 100; let after: string | undefined = undefined; for(let i = 0; i < 1000; i++) { console.log(`Fetching companies, iteration ${i+1}`); const response = await hubspotClient.crm.companies.basicApi.getPage(limit, after); // console.log(response.results); const companies: Company[] = response.results.map((company) => CompanySchema.parse({ id: company.id, name: company.properties.name ?? '', })); allCompanies.push(...companies); if(response.paging && response.paging.next && response.paging.next.after) { after = response.paging.next.after; continue; } break; } return allCompanies; } catch (error) { console.error("Error fetching companies:", error); return null; } }, getOwners: async(): Promise => { try { const allOwners: Owner[] = []; const limit = 100; let after: string | undefined = undefined; for(let i = 0; i < 1000; i++) { console.log(`Fetching owners, iteration ${i+1}`); const response = await hubspotClient.crm.owners.ownersApi.getPage(undefined,after,limit); // console.log(response.results); const owners: Owner[] = response.results.map((owner) => OwnerSchema.parse({ id: owner.id, email: owner.email, })); allOwners.push(...owners); if(response.paging && response.paging.next && response.paging.next.after) { after = response.paging.next.after; continue; } break; } return allOwners; } catch (error) { console.error("Error fetching owners:", error); return null; } }, createMeetingLog: async(companyId: string, title: string, userId: string | null, minutes: string, startsAt: string, endsAt: string ): Promise => { try { // 改行コードを変換 const minutes_html = minutes.replace("\n", "
") const associations: PublicAssociationsForObject[] = [{ types: [ {associationCategory: AssociationSpecAssociationCategoryEnum.HubspotDefined, associationTypeId: 188}, ], to: {id: companyId}, }]; const properties = { hs_timestamp: startsAt, hs_meeting_title: title, hubspot_owner_id: userId || '', hs_meeting_body: minutes_html, hs_meeting_start_time: startsAt, hs_meeting_end_time: endsAt, } const result = await hubspotClient.crm.objects.meetings.basicApi.create({ associations: associations, properties: properties, }); return true; } catch (error) { console.error("Error creating HubSpot meeting log:", error); return false; } }, searchOwnerIdByEmail: (email: string, owners: Owner[]): string | null => { for(const owner of owners) { if(email === owner.email) return owner.id; } return null; }, };