Prompt

When a tool’s calculation is simple, you can simply return its value to the Latitude SDK, as shown in the prompt with tools example. However, for more complex calculations, you can pause the execution of the tool, process the data asynchronously, and then respond with the result in the same conversation.

---
provider: Latitude
model: gpt-4o-mini
tools:
  - generate_travel_itinerary:
      description: Generates a personalized multi-day travel itinerary for a user based on their preferences, location, and available dates. This requires multiple external data sources and can take some time, so it runs as a background job.
      parameters:
        type: object
        additionalProperties: false
        required: ['destination', 'start_date', 'end_date', 'preferences', 'user_id']
        properties:
          destination:
            type: string
            description: Name of the travel destination (city, country, etc.)
          start_date:
            type: string
            description: Start date of the trip (YYYY-MM-DD)
          end_date:
            type: string
            description: End date of the trip (YYYY-MM-DD)
          preferences:
            type: array
            items:
              type: string
            description: List of user interests (e.g., museums, food, outdoor, art)
          user_id:
            type: string
            description: Unique identifier for the requesting user
---

Plan my trip to {{ destination }} from {{ start_date }} to {{ end_date }}.
I like {{ preferences.join(', ') }}.

# Example response to user

Great! I’m planning your trip to {{ destination }} with your preferences.
This may take a few minutes, as I’ll be gathering up-to-date info from multiple sources. I’ll notify you as soon as your custom itinerary is ready!

Code

In this example, you can see how itinerary creation is requested by the AI. The execution is paused, the data is stored (in memory, though you could also store it in your database or Redis), and then the tool execution is resumed with the calculated itinerary.

import { Latitude } from '@latitude-data/sdk'
import { Message, MessageRole } from 'promptl-ai'

// You can type the tools you are using
type Tools = {
  generate_travel_itinerary: {
    location: string
    start_date: string
    end_date: string
    preferences: string
  }
}

type ItineraryRequested = {
  data: {
    location: string
    start_date: string
    end_date: string
    preferences: string
  }
  toolId: string
  toolName: string
  conversationUuid: string
  previousMessages: Message[]
}

let toolRequested: ItineraryRequested | undefined

function enqueueJobToProcessItinerary(itinerary: ItineraryRequested) {
  toolRequested = itinerary
}

function computeTravelItinerary(itinerary: ItineraryRequested) {
  return {
    location: itinerary.data.location,
    start_date: itinerary.data.start_date,
    end_date: itinerary.data.end_date,
    preferences: itinerary.data.preferences,
    recomendations: [
      'Visit the Sagrada Familia',
      'Explore Park Güell',
      'Take a stroll down La Rambla',
      'Relax at Barceloneta Beach',
      'Enjoy tapas at a local restaurant',
      'Visit the Picasso Museum',
    ],
  }
}

async function run() {
  const sdk = new Latitude(process.env.LATITUDE_API_KEY, {
    projectId: Number(process.env.PROJECT_ID),
    versionUuid: 'live',
  })

  await sdk.prompts.run<Tools>('pause-tools/example', {
    parameters: {
      destination: 'Barcelona',
      start_date: '2025-06-02',
      end_date: '2025-06-10',
      preferences: 'museums, parks, and local cuisine',
    },
    tools: {
      generate_travel_itinerary: async (
        data,
        { messages, conversationUuid, toolId, toolName, pauseExecution },
      ) => {
        enqueueJobToProcessItinerary({
          data,
          toolId,
          toolName,
          conversationUuid,
          previousMessages: messages,
        })

        // You are not returning the result now because the computation
        // is heavy and you want to pause the execution
        return pauseExecution()
      },
    },
  })

  // Imagine this is your backend processing the job
  if (toolRequested) {
    const result = await sdk.prompts.chat(toolRequested.conversationUuid, [
      {
        role: MessageRole.tool,
        content: [
          {
            type: 'tool-result',
            toolName: toolRequested.toolName,
            toolCallId: toolRequested.toolId,
            result: computeTravelItinerary(toolRequested),
          },
        ],
      },
    ])

    console.log('Recomendation', result.response.text)
  }
}

run()