// Documenso API client utilities interface DocumensoConfig { apiUrl: string; apiKey: string; } interface DocumensoRecipient { id: number; documentId: number; email: string; name: string; role: 'SIGNER' | 'APPROVER' | 'VIEWER'; signingOrder: number; token: string; signedAt: string | null; readStatus: 'NOT_OPENED' | 'OPENED'; signingStatus: 'NOT_SIGNED' | 'SIGNED'; sendStatus: 'NOT_SENT' | 'SENT'; signingUrl: string; } interface DocumensoDocument { id: number; externalId: string; userId: number; teamId: number; title: string; status: 'DRAFT' | 'PENDING' | 'COMPLETED' | 'CANCELLED'; documentDataId: string; createdAt: string; updatedAt: string; completedAt: string | null; recipients: DocumensoRecipient[]; } interface DocumensoListResponse { documents: DocumensoDocument[]; total: number; page: number; perPage: number; } // Get Documenso configuration from environment variables const getDocumensoConfig = (): DocumensoConfig => { const apiUrl = process.env.NUXT_DOCUMENSO_BASE_URL; const apiKey = process.env.NUXT_DOCUMENSO_API_KEY; if (!apiUrl || !apiKey) { throw createError({ statusCode: 500, statusMessage: 'Documenso configuration missing. Please check NUXT_DOCUMENSO_BASE_URL and NUXT_DOCUMENSO_API_KEY environment variables.' }); } return { apiUrl: `${apiUrl}/api/v1`, apiKey: `Bearer ${apiKey}` }; }; // Fetch a single document by ID export const getDocumensoDocument = async (documentId: number): Promise => { const config = getDocumensoConfig(); try { const response = await $fetch(`${config.apiUrl}/documents/${documentId}`, { headers: { 'Authorization': config.apiKey, 'Content-Type': 'application/json' } }); return response; } catch (error) { console.error('Failed to fetch Documenso document:', error); throw error; } }; // Search documents by external ID (e.g., 'loi-94') export const searchDocumensoDocuments = async (externalId?: string): Promise => { const config = getDocumensoConfig(); try { const response = await $fetch(`${config.apiUrl}/documents`, { headers: { 'Authorization': config.apiKey, 'Content-Type': 'application/json' }, params: { perPage: 100 } }); // If externalId is provided, filter by it if (externalId) { return response.documents.filter((doc: DocumensoDocument) => doc.externalId === externalId); } return response.documents; } catch (error) { console.error('Failed to search Documenso documents:', error); throw error; } }; // Get document by external ID (e.g., 'loi-94') export const getDocumensoDocumentByExternalId = async (externalId: string): Promise => { const documents = await searchDocumensoDocuments(externalId); return documents.length > 0 ? documents[0] : null; }; // Check signature status for a document export const checkDocumentSignatureStatus = async (documentId: number): Promise<{ documentStatus: string; unsignedRecipients: DocumensoRecipient[]; signedRecipients: DocumensoRecipient[]; clientSigned: boolean; allSigned: boolean; }> => { const document = await getDocumensoDocument(documentId); const unsignedRecipients = document.recipients.filter((r: DocumensoRecipient) => r.signingStatus === 'NOT_SIGNED'); const signedRecipients = document.recipients.filter((r: DocumensoRecipient) => r.signingStatus === 'SIGNED'); // Check if client (signingOrder = 1) has signed const clientRecipient = document.recipients.find((r: DocumensoRecipient) => r.signingOrder === 1); const clientSigned = clientRecipient ? clientRecipient.signingStatus === 'SIGNED' : false; const allSigned = unsignedRecipients.length === 0; return { documentStatus: document.status, unsignedRecipients, signedRecipients, clientSigned, allSigned }; }; // Get recipients who need to sign (excluding client) export const getRecipientsToRemind = async (documentId: number): Promise => { const status = await checkDocumentSignatureStatus(documentId); // Only remind if client has signed if (!status.clientSigned) { return []; } // Return unsigned recipients with signingOrder > 1 return status.unsignedRecipients.filter((r: DocumensoRecipient) => r.signingOrder > 1); }; // Format recipient name for emails export const formatRecipientName = (recipient: DocumensoRecipient): string => { const firstName = recipient.name.split(' ')[0]; return firstName; }; // Get signing URL for a recipient export const getSigningUrl = (recipient: DocumensoRecipient): string => { return recipient.signingUrl; };