UNPKG

@adonis-agora/agent

Version:

Governed, durable-backed AI agent (chat + tool-calling + governance) for AdonisJS — part of the Agora ecosystem.

84 lines • 5 kB
import { ptBrActionProposalText, } from '../action-proposal-text.js'; import { humanizeToolName, resolveToolConfirmation, } from '../tool-presentation.js'; import { DEFAULT_CHANNEL_QUESTION_TEXTS, ptBrChannelQuestionTexts, } from './questions.js'; /** `20 MB`, `512 KB`. */ const readableSize = (bytes) => bytes >= 1024 * 1024 ? `${Math.round(bytes / (1024 * 1024))} MB` : `${Math.max(1, Math.ceil(bytes / 1024))} KB`; export const DEFAULT_CHANNEL_TEXTS = { approve: 'Confirm', reject: 'Cancel', proposal: ({ confirmation, toolName }) => confirmation ? `*${confirmation.title}*${confirmation.detail ? `\n${confirmation.detail}` : ''}` : `*${resolveToolConfirmation(toolName, undefined).title}*`, instruction: ({ approve, reject }) => `Reply *${approve}* to confirm or *${reject}* to cancel.`, blockingApproval: 'This action needs an approval that can only be given in the app.', failed: 'Sorry, something went wrong. Please try again.', linkInstruction: 'Open the link to continue.', linkValidity: (minutes) => `The link works for up to ${minutes} minutes.`, actionSucceeded: 'Done.', actionFailed: 'The action could not be completed.', noPendingConfirmation: 'There is nothing waiting for your confirmation here.', ambiguousDecision: (ids, { approve, reject }) => `Which one? Reply *${approve} #ID* or *${reject} #ID*: ${ids.map((id) => `#${id}`).join(', ')}`, rememberRefused: 'Here every action needs its own confirmation. Reply without "always".', mediaRefused: (reason, media, limits) => reason === 'disabled' ? 'I can only read text messages here.' : reason === 'size' ? `That file is too large${limits ? ` (the limit is ${readableSize(limits.maxBytes)})` : ''}.` : reason === 'failed' ? 'I could not download that file. Please send it again.' : media.kind === 'audio' ? 'I cannot listen to audio messages. Please type your message.' : `I cannot read this kind of file${media.contentType ? ` (${media.contentType})` : ''}.`, questions: DEFAULT_CHANNEL_QUESTION_TEXTS, }; /** * Brazilian Portuguese channel texts — the default when the agent's `actionProposalText` is * `ptBrActionProposalText`, so the reply words and what the channel says agree. */ export const ptBrChannelTexts = { approve: 'Confirmar', reject: 'Cancelar', proposal: ({ confirmation, toolName }) => confirmation ? `*${confirmation.title}*${confirmation.detail ? `\n${confirmation.detail}` : ''}` : `*Executar: ${humanizeToolName(toolName) || 'ação'}?*`, instruction: ({ approve, reject }) => `Responda *${approve}* para confirmar ou *${reject}* para cancelar.`, blockingApproval: 'Esta ação precisa de uma aprovação que só pode ser dada no app.', failed: 'Desculpe, algo deu errado. Tente de novo, por favor.', linkInstruction: 'Abra o link para continuar.', linkValidity: (minutes) => `O link vale por até ${minutes} minutos.`, actionSucceeded: 'Pronto.', actionFailed: 'Não foi possível concluir a ação.', noPendingConfirmation: 'Não há nenhuma confirmação pendente por aqui.', ambiguousDecision: (ids, { approve, reject }) => `Qual delas? Responda *${approve} #ID* ou *${reject} #ID*: ${ids.map((id) => `#${id}`).join(', ')}`, rememberRefused: 'Por aqui cada ação precisa da sua própria confirmação. Responda sem o "sempre".', mediaRefused: (reason, media, limits) => reason === 'disabled' ? 'Por aqui eu só consigo ler mensagens de texto.' : reason === 'size' ? `Esse arquivo é grande demais${limits ? ` (o limite é ${readableSize(limits.maxBytes)})` : ''}.` : reason === 'failed' ? 'Não consegui baixar esse arquivo. Envie de novo, por favor.' : media.kind === 'audio' ? 'Não consigo ouvir mensagens de áudio. Escreva sua mensagem, por favor.' : `Não consigo ler esse tipo de arquivo${media.contentType ? ` (${media.contentType})` : ''}.`, questions: ptBrChannelQuestionTexts, }; /** * The channel texts that speak the language of the agent's text-decision words: {@link * ptBrChannelTexts} for `ptBrActionProposalText` (or any vocabulary whose `language` is Portuguese), * else {@link DEFAULT_CHANNEL_TEXTS}. */ export function channelTextsFor(vocabulary) { if (!vocabulary) return DEFAULT_CHANNEL_TEXTS; const portuguese = /^pt(-|$)/i.test(vocabulary.language ?? '') || vocabulary.approve === ptBrActionProposalText.vocabulary.approve; return portuguese ? ptBrChannelTexts : DEFAULT_CHANNEL_TEXTS; } /** `overrides` over `base`, `questions` merged too. */ export const mergeTexts = (overrides = {}, base = DEFAULT_CHANNEL_TEXTS) => ({ ...base, ...overrides, questions: { ...base.questions, ...overrides.questions }, }); //# sourceMappingURL=texts.js.map