Skip to main content
Glama
setup-medplum-agent.ts4.68 kB
// SPDX-FileCopyrightText: Copyright Orangebot, Inc. and Medplum contributors // SPDX-License-Identifier: Apache-2.0 import { createReference, getAllQuestionnaireAnswers, getReferenceString } from '@medplum/core'; import type { BotEvent, MedplumClient } from '@medplum/core'; import type { AgentChannel, Bot, Endpoint, QuestionnaireResponse } from '@medplum/fhirtypes'; export async function handler(medplum: MedplumClient, event: BotEvent<QuestionnaireResponse>): Promise<void> { const response = event.input; const answers = getAllQuestionnaireAnswers(response); // Create an organization representing the remote site const organizationName = answers['organization-name']?.[0]?.valueString; if (!organizationName) { throw new Error('Missing organization name'); } const organization = await medplum.upsertResource( { resourceType: 'Organization', name: organizationName, }, { name: organizationName } ); /* Inbound Communications */ const endpoints = await Promise.all( answers['endpoint-name'].map((endpointName, index) => { const endpointAddress = answers['endpoint-ip']?.at(index)?.valueString; const endpointPort = answers['endpoint-port']?.at(index)?.valueInteger; const identifier = toIdentifier(endpointName.valueString ?? ''); const endpoint: Endpoint = { resourceType: 'Endpoint', name: endpointName?.valueString, identifier: [ { system: 'http://example.com', value: identifier, }, ], status: 'active', managingOrganization: createReference(organization), connectionType: { system: 'http://terminology.hl7.org/CodeSystem/endpoint-connection-type', code: 'hl7v2-mllp', display: 'HL7 v2 MLLP', }, payloadType: [ { coding: [ { system: 'http://terminology.hl7.org/CodeSystem/endpoint-payload-type', code: 'any', display: 'Any', }, ], }, ], address: `mllp://${endpointAddress}:${endpointPort}`, }; return medplum.upsertResource(endpoint, { organization: getReferenceString(organization), identifier, }); }) ); // Create a new Bot to listen on each agent channel const projectId = medplum.getProject()?.id; const bots = await Promise.all( endpoints.map(async (endpoint) => { return medplum.post(`/admin/projects/${projectId}/bot`, { name: `${organization.name}: ${endpoint.name} [Inbound]`, }) as Promise<Bot>; }) ); // Create the Agent resource, that represents the Medplum agent installed on-site const agentId = { system: 'http://example.com/agent-id', value: toIdentifier(organizationName) + '-agent', }; const agent = await medplum.upsertResource( { resourceType: 'Agent', status: 'active', name: `${organization.name} Agent`, identifier: [agentId], channel: endpoints.map( (endpoint, index): AgentChannel => ({ name: endpoint.name ?? '', endpoint: createReference(endpoint), targetReference: createReference(bots[index]), }) ), }, { identifier: `${agentId.system}|${agentId.value}`, } ); // Create a ClientApplication to provide manage credentials for the on-site Agent await medplum.post(`admin/projects/${projectId}/client`, { name: `${agent.name} Client`, description: `Client ID/Secret for ${agent.name}`, }); /* Outbound Communication */ // Set up Device resources for remote devices (e.g. remote EMR, LIS, or RIS systems) await Promise.all( answers['device-name'].map((deviceName, index) => { const ip = answers['device-address']?.at(index)?.valueString; const port = answers['device-port']?.at(index)?.valueInteger; const deviceId = `${toIdentifier(organizationName)}-${toIdentifier(deviceName.valueString ?? '')}`; return medplum.upsertResource( { resourceType: 'Device', identifier: [{ system: 'http://example.com/device-id', value: deviceId }], deviceName: [{ name: deviceName.valueString ?? '', type: 'user-friendly-name' }], url: `mllp://${ip}:${port}`, }, { identifier: deviceId } ); }) ); // Create a placeholder Bot to handle outbound communications await medplum.post(`/admin/projects/${projectId}/bot`, { name: `${organization.name} [Outbound]`, }); } function toIdentifier(s: string): string { return s.toLowerCase().replaceAll(/(\s+|\.+)/g, '-'); }

Latest Blog Posts

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/medplum/medplum'

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