Introduzione alle chiamate di funzione

I modelli linguistici di grandi dimensioni (LLM) sono molto efficaci per risolvere molti tipi di problemi. Tuttavia, sono soggetti alle seguenti limitazioni:

  • Vengono bloccati dopo l'addestramento, il che porta a conoscenze obsolete.
  • Non possono eseguire query o modificare i dati esterni.

La chiamata di funzioni può risolvere questi problemi. A volte la chiamata di funzione viene definita utilizzo di strumenti perché consente al modello di utilizzare strumenti esterni come API e funzioni.

Quando invii un prompt all'LLM, fornisci anche al modello un insieme di strumenti che può utilizzare per rispondere al prompt dell'utente. Ad esempio, potresti fornire una funzione get_weather che accolga un parametro di posizione e restituisca informazioni sulle condizioni meteorologiche in quella posizione.

Durante l'elaborazione di un prompt, il modello può scegliere di delegare determinate attività di elaborazione dei dati alle funzioni che identifichi. Il modello non chiama direttamente le funzioni. Il modello fornisce invece un'uscita di dati strutturati che include la funzione da chiamare e i valori dei parametri da utilizzare. Ad esempio, per un prompt What is the weather like in Boston?, il modello può delegare l'elaborazione alla funzione get_weather e fornire il valore parametro posizione Boston, MA.

Puoi utilizzare l'output strutturato del modello per richiamare API esterne. Ad esempio, puoi connetterti a un'API di servizio meteo, fornire la posizioneBoston, MA e ricevere informazioni su temperatura, copertura nuvolosa e condizioni di vento.

Puoi quindi fornire l'output dell'API al modello, consentendogli di completare la risposta al prompt. Per l'esempio sul meteo, il modello potrebbe fornire la seguente risposta: It is currently 38 degrees Fahrenheit in Boston, MA with partly cloudy skies.

Interazione di chiamata di funzione 

Modelli supportati

I seguenti modelli forniscono supporto per la chiamata di funzioni:

Modello Versione Fase di lancio delle chiamate di funzione Supporto per le chiamate di funzioni parallele Supporto per la chiamata di funzioni forzata
Gemini 1.0 Pro all versions Disponibilità generale No No
Gemini 1.5 Flash all versions Disponibilità generale
Gemini 1.5 Pro all versions Disponibilità generale

Casi d'uso della chiamata di funzioni

Puoi utilizzare le chiamate di funzione per le seguenti attività:

Caso d'uso Descrizione di esempio Link di esempio
Integrazione con API esterne Ottenere informazioni meteo utilizzando un'API meteorologica Tutorial su Notebook
Convertire gli indirizzi in coordinate di latitudine/longitudine Tutorial su Notebook
Convertire le valute utilizzando un'API di cambio valuta Codelab
Creare chatbot avanzati Rispondere alle domande dei clienti su prodotti e servizi Tutorial su Notebook
Creare un assistente per rispondere a domande finanziarie e di notizie sulle aziende Tutorial su Notebook
Struttura e controlla le chiamate alle funzioni Estrare entità strutturate dai dati non elaborati dei log Tutorial su Notebook
Estrarre uno o più parametri dall'input utente Tutorial su Notebook
Gestire elenchi e strutture di dati nidificate nelle chiamate di funzione Tutorial su Notebook
Gestire il comportamento di chiamata delle funzioni Gestire chiamate e risposte di funzioni parallele Tutorial su Notebook
Gestire quando e quali funzioni può chiamare il modello Tutorial su Notebook
Esegui query sui database con il linguaggio naturale Converti le domande in linguaggio naturale in query SQL per BigQuery App di esempio
Chiamate di funzioni multimodali Utilizza immagini, video, audio e PDF come input per attivare le chiamate di funzione Tutorial su Notebook

Ecco altri casi d'uso:

  • Interpreta i comandi vocali: crea funzioni corrispondenti alle attività nel veicolo. Ad esempio, puoi creare funzioni che accendano la radio o attivino l'aria condizionata. Invia al modello i file audio dei comandi vocali dell'utente e chiedigli di convertire l'audio in testo e di identificare la funzione che l'utente vuole chiamare.

  • Automatizza i flussi di lavoro in base a trigger ambientali: crea funzioni per rappresentare i processi che possono essere automatizzati. Fornisci al modello i dati dei sensori ambientali e chiedigli di analizzarli ed elaborarli per determinare se attivare uno o più flussi di lavoro. Ad esempio, un modello potrebbe elaborare i dati sulla temperatura in un magazzino e scegliere di attivare una funzione di irrigazione.

  • Automatizza l'assegnazione dei ticket di assistenza: fornisci al modello ticket di assistenza, log e regole basate sul contesto. Chiedi al modello di elaborare tutte queste informazioni per determinare a chi deve essere assegnato il ticket. Chiama una funzione per assegnare il ticket alla persona suggerita dal modello.

  • Recupero di informazioni da una knowledge base: crea funzioni che recuperono articoli accademici su un determinato argomento e li riassumono. Consenti al modello di rispondere a domande su materie accademiche e di fornire citazioni per le sue risposte.

Come creare un'applicazione di chiamata di funzioni

Per consentire a un utente di interagire con il modello e utilizzare la chiamata di funzioni, devi creare codice che esegua le seguenti attività:

  1. Configura l'ambiente.
  2. Definire e descrivere un insieme di funzioni disponibili utilizzando le dichiarazioni di funzione.
  3. Invia al modello la richiesta di un utente e le dichiarazioni delle funzioni.
  4. Esegui una chiamata a una funzione utilizzando l'output dei dati strutturati del modello.
  5. Fornisci l'output della funzione al modello.

Puoi creare un'applicazione che gestisce tutte queste attività. Questa applicazione può essere un chatbot di testo, un agente vocale, un flusso di lavoro automatico o qualsiasi altro programma.

Puoi utilizzare le chiamate di funzione per generare una singola risposta di testo o per supportare una sessione di chat. Le risposte di testo ad hoc sono utili per attività aziendali specifiche, inclusa la generazione di codice. Le sessioni di chat sono utili in scenari di conversazione in formato libero, in cui è probabile che un utente ponga domande di follow-up.

Se utilizzi la chiamata di funzione per generare una singola risposta, devi fornire al modello il contesto completo dell'interazione. Se invece utilizzi la chiamata di funzione nel contesto di una sessione di chat, la sessione memorizza il contesto per te e lo include in ogni richiesta al modello. In entrambi i casi, Vertex AI memorizza la cronologia dell'interazione lato client.

Questa guida mostra come utilizzare la chiamata di funzione per generare una singola risposta di testo. Per un esempio end-to-end, consulta Esempi di testo. Per scoprire come utilizzare le chiamate di funzione per supportare una sessione di chat, consulta Esempi di chat.

Passaggio 1: configura l'ambiente

Importa i moduli richiesti e inizializza il modello:

Python

import vertexai
from vertexai.generative_models import (
    Content,
    FunctionDeclaration,
    GenerationConfig,
    GenerativeModel,
    Part,
    Tool,
)

# Initialize Vertex AI
# TODO(developer): Update and un-comment below lines
# PROJECT_ID = 'your-project-id'
vertexai.init(project=PROJECT_ID, location="us-central1")

# Initialize Gemini model
model = GenerativeModel(model_name="gemini-1.5-flash-002")

Passaggio 2: dichiara un insieme di funzioni

L'applicazione deve dichiarare un insieme di funzioni che il modello può utilizzare per elaborare il prompt.

Il numero massimo di dichiarazioni di funzioni che possono essere fornite con la richiesta è 128.

Devi fornire le dichiarazioni di funzione in un formato dello schema compatibile con lo schema OpenAPI. Vertex AI offre un supporto limitato dello schema OpenAPI. I seguenti attributi sono supportati: type, nullable, required, format, description, properties, items, enum. I seguenti attributi non sono supportati: default, optional, maximum, oneOf. Per le best practice relative alle dichiarazioni di funzione, inclusi suggerimenti per nomi e descrizioni, consulta Best practice.

Se utilizzi l'API REST, specifica lo schema utilizzando JSON. Se utilizzi l'SDK Vertex AI per Python, puoi specificare lo schema manualmente utilizzando un dizionario Python o automaticamente con la funzione di assistenza from_func.

JSON

{
  "contents": ...,
  "tools": [
    {
      "function_declarations": [
        {
          "name": "find_movies",
          "description": "find movie titles currently playing in theaters based on any description, genre, title words, etc.",
          "parameters": {
            "type": "object",
            "properties": {
              "location": {
                "type": "string",
                "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
              },
              "description": {
                "type": "string",
                "description": "Any kind of description including category or genre, title words, attributes, etc."
              }
            },
            "required": [
              "description"
            ]
          }
        },
        {
          "name": "find_theaters",
          "description": "find theaters based on location and optionally movie title which are is currently playing in theaters",
          "parameters": {
            "type": "object",
            "properties": {
              "location": {
                "type": "string",
                "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
              },
              "movie": {
                "type": "string",
                "description": "Any movie title"
              }
            },
            "required": [
              "location"
            ]
          }
        },
        {
          "name": "get_showtimes",
          "description": "Find the start times for movies playing in a specific theater",
          "parameters": {
            "type": "object",
            "properties": {
              "location": {
                "type": "string",
                "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
              },
              "movie": {
                "type": "string",
                "description": "Any movie title"
              },
              "theater": {
                "type": "string",
                "description": "Name of the theater"
              },
              "date": {
                "type": "string",
                "description": "Date for requested showtime"
              }
            },
            "required": [
              "location",
              "movie",
              "theater",
              "date"
            ]
          }
        }
      ]
    }
  ]
}

Dizionario Python

La seguente dichiarazione di funzione accetta un singolo parametro string:

function_name = "get_current_weather"
get_current_weather_func = FunctionDeclaration(
    name=function_name,
    description="Get the current weather in a given location",
    # Function parameters are specified in JSON schema format
    parameters={
        "type": "object",
        "properties": {
            "location": {"type": "string", "description": "The city name of the location for which to get the weather."}
        },
    },
)

La seguente dichiarazione di funzione accetta parametri sia di oggetti che di array:

extract_sale_records_func = FunctionDeclaration(
  name="extract_sale_records",
  description="Extract sale records from a document.",
  parameters={
      "type": "object",
      "properties": {
          "records": {
              "type": "array",
              "description": "A list of sale records",
              "items": {
                  "description": "Data for a sale record",
                  "type": "object",
                  "properties": {
                      "id": {"type": "integer", "description": "The unique id of the sale."},
                      "date": {"type": "string", "description": "Date of the sale, in the format of MMDDYY, e.g., 031023"},
                      "total_amount": {"type": "number", "description": "The total amount of the sale."},
                      "customer_name": {"type": "string", "description": "The name of the customer, including first name and last name."},
                      "customer_contact": {"type": "string", "description": "The phone number of the customer, e.g., 650-123-4567."},
                  },
                  "required": ["id", "date", "total_amount"],
              },
          },
      },
      "required": ["records"],
  },
)

Python dalla funzione

Il seguente esempio di codice dichiara una funzione che moltiplica un array di numeri e utilizza from_func per generare lo schema FunctionDeclaration.

# Define a function. Could be a local function or you can import the requests library to call an API
def multiply_numbers(numbers):
  """
  Calculates the product of all numbers in an array.

  Args:
      numbers: An array of numbers to be multiplied.

  Returns:
      The product of all the numbers. If the array is empty, returns 1.
  """

  if not numbers:  # Handle empty array
      return 1

  product = 1
  for num in numbers:
      product *= num

  return product

multiply_number_func = FunctionDeclaration.from_func(multiply_numbers)

'''
multiply_number_func contains the following schema:

name: "multiply_numbers"
description: "Calculates the product of all numbers in an array."
parameters {
  type_: OBJECT
  properties {
    key: "numbers"
    value {
      description: "An array of numbers to be multiplied."
      title: "Numbers"
    }
  }
  required: "numbers"
  description: "Calculates the product of all numbers in an array."
  title: "multiply_numbers"
}
'''

Passaggio 3: invia le dichiarazioni del prompt e delle funzioni al modello

Quando l'utente fornisce un prompt, l'applicazione deve fornire al modello il prompt dell'utente e le dichiarazioni di funzione. Per configurare il modo in cui il modello genera i risultati, l'applicazione può fornire al modello una configurazione di generazione. Per configurare il modo in cui il modello utilizza le dichiarazioni di funzione, l'applicazione può fornire al modello una configurazione dello strumento.

Definire la richiesta all'utente

Di seguito è riportato un esempio di prompt dell'utente: "Che tempo fa a Boston?"

Di seguito è riportato un esempio di come definire la richiesta all'utente:

Python

# Define the user's prompt in a Content object that we can reuse in model calls
user_prompt_content = Content(
    role="user",
    parts=[
        Part.from_text("What is the weather like in Boston?"),
    ],
)

Per le best practice relative alla richiesta all'utente, consulta Best practice - Richiesta all'utente.

Configurazione della generazione

Il modello può generare risultati diversi per valori parametro diversi. Il parametro temperatura controlla il grado di casualità in questa generazione. Le temperature più basse sono ideali per le funzioni che richiedono valori parametro deterministici, mentre le temperature più alte sono ideali per le funzioni con parametri che accettano valori parametro più diversificati o creativi. Una temperatura pari a 0 è deterministica. In questo caso, le risposte per un determinato prompt sono per lo più predeterminate, ma è ancora possibile una piccola variazione. Per scoprire di più, consulta l'API Gemini.

Per impostare questo parametro, invia una configurazione di generazione (generation_config) insieme al prompt e alle dichiarazioni delle funzioni. Puoi aggiornare il parametro temperature durante una conversazione di chat utilizzando l'API Vertex AI e un generation_config aggiornato. Per un esempio di impostazione del parametro temperature, consulta Come inviare il prompt e le dichiarazioni delle funzioni.

Per le best practice relative alla configurazione della generazione, consulta Best practice - Configurazione della generazione.

Configurazione dello strumento

Puoi applicare alcuni vincoli al modo in cui il modello deve utilizzare le dichiarazioni di funzione che fornisci. Ad esempio, anziché consentire al modello di scegliere tra una risposta in linguaggio naturale e una chiamata di funzione, puoi costringerlo a prevedere solo le chiamate di funzione ("chiamate di funzione forzate" o "chiamate di funzione con generazione controllata"). Puoi anche scegliere di fornire al modello un insieme completo di dichiarazioni di funzioni, ma limitare le sue risposte a un sottoinsieme di queste funzioni.

Per applicare questi vincoli, invia una configurazione dello strumento (tool_config) insieme al prompt e alle dichiarazioni di funzione. Nella configurazione, puoi specificare una delle seguenti modalità:

Modalità Descrizione
AUTO Il comportamento predefinito del modello. Il modello decide se prevedere chiamate di funzione o una risposta in linguaggio naturale.
ANY Il modello è vincolato a prevedere sempre una chiamata di funzione. Se non viene fornito allowed_function_names, il modello sceglie tra tutte le dichiarazioni di funzione disponibili. Se viene fornito allowed_function_names, il modello sceglie dall'insieme di funzioni consentite.
NONE Il modello non deve prevedere le chiamate di funzione. Questo comportamento è equivalente a una richiesta di modello senza dichiarazioni di funzioni associate.

Per un elenco dei modelli che supportano la modalità ANY ("chiamata di funzione forzata"), consulta i modelli supportati.

Per saperne di più, consulta l'API Call Function.

Come inviare il prompt e le dichiarazioni di funzione

Di seguito è riportato un esempio di come inviare il prompt e le dichiarazioni di funzione al modello e vincolarlo a prevedere solo le chiamate di funzione get_current_weather.

Python

# Define a tool that includes some of the functions that we declared earlier
tool = Tool(
    function_declarations=[get_current_weather_func, extract_sale_records_func, multiply_number_func],
)

# Send the prompt and instruct the model to generate content using the Tool object that you just created
response = model.generate_content(
    user_prompt_content,
    generation_config=GenerationConfig(temperature=0),
    tools=[tool],
    tool_config=ToolConfig(
        function_calling_config=ToolConfig.FunctionCallingConfig(
            # ANY mode forces the model to predict only function calls
            mode=ToolConfig.FunctionCallingConfig.Mode.ANY,
            # Allowed function calls to predict when the mode is ANY. If empty, any  of
            # the provided function calls will be predicted.
            allowed_function_names=["get_current_weather"],
        )
    )
)

Se il modello determina di aver bisogno dell'output di una determinata funzione, la risposta che l'applicazione riceve dal modello contiene il nome della funzione e i valori dei parametri con cui deve essere chiamata la funzione.

Di seguito è riportato un esempio di risposta del modello al prompt dell'utente "Che tempo fa a Boston?". Il modello propone di chiamare la funzione get_current_weather con il parametro Boston, MA.

candidates {
  content {
    role: "model"
    parts {
      function_call {
        name: "get_current_weather"
        args {
          fields {
            key: "location"
            value {
              string_value: "Boston, MA"
            }
          }
        }
      }
    }
  }
  ...
}

Per prompt come "Vorrei avere i dettagli meteo di New Delhi e San Francisco", il modello potrebbe proporre diverse chiamate di funzioni in parallelo. Per saperne di più, consulta l'esempio di chiamata di funzione parallela.

Passaggio 4: richiama un'API esterna

Se l'applicazione riceve un nome di funzione e valori di parametro dal modello, deve connettersi a un'API esterna e chiamare la funzione.

Il seguente esempio utilizza dati sintetici per simulare un payload di risposta di un'API esterna:

Python

# Check the function name that the model responded with, and make an API call to an external system
if (response.candidates[0].function_calls[0].name == "get_current_weather"):
    # Extract the arguments to use in your API call
    location = response.candidates[0].function_calls[0].args["location"]

    # Here you can use your preferred method to make an API request to fetch the current weather, for example:
    # api_response = requests.post(weather_api_url, data={"location": location})

    # In this example, we'll use synthetic data to simulate a response payload from an external API
    api_response = """{ "location": "Boston, MA", "temperature": 38, "description": "Partly Cloudy",
                    "icon": "partly-cloudy", "humidity": 65, "wind": { "speed": 10, "direction": "NW" } }"""

Per le best practice relative all'invocazione dell'API, consulta Best practice - Invocazione dell'API.

Passaggio 5: fornisci l'output della funzione al modello

Dopo che un'applicazione riceve una risposta da un'API esterna, deve fornire questa risposta al modello. Di seguito è riportato un esempio di come eseguire questa operazione utilizzando Python:

Python

response = model.generate_content(
    [
        user_prompt_content,  # User prompt
        response.candidates[0].content,  # Function call response
        Content(
            parts=[
                Part.from_function_response(
                    name="get_current_weather",
                    response={
                        "content": api_response,  # Return the API response to Gemini
                    },
                )
            ],
        ),
    ],
    tools=[weather_tool],
)
# Get the model summary response
summary = response.text

Se il modello ha proposto più chiamate di funzione in parallelo, l'applicazione deve fornire tutte le risposte al modello. Per saperne di più, consulta Esempio di chiamata di funzioni parallele.

Il modello potrebbe stabilire che l'output di un'altra funzione è necessario per rispondere al prompt. In questo caso, la risposta che l'applicazione riceve dal modello contiene un altro nome di funzione e un altro insieme di valori di parametro.

Se il modello determina che la risposta dell'API è sufficiente per rispondere al prompt dell'utente, crea una risposta in linguaggio naturale e la restituisce all'applicazione. In questo caso, l'applicazione deve ritrasmettere la risposta all'utente. Di seguito è riportato un esempio di risposta:

It is currently 38 degrees Fahrenheit in Boston, MA with partly cloudy skies. The humidity is 65% and the wind is blowing at 10 mph from the northwest.

Esempi di chiamata di funzione

Esempi di testo

Puoi utilizzare le chiamate di funzione per generare una singola risposta di testo. Le risposte con testo ad hoc sono utili per attività aziendali specifiche, inclusa la generazione di codice.

Se utilizzi la chiamata di funzione per generare una singola risposta, devi fornire al modello il contesto completo dell'interazione. Vertex AI memorizza la cronologia dell'interazione lato client.

Python

Questo esempio mostra uno scenario di testo con una funzione e un prompt. Utilizza la classe GenerativeModel e i relativi metodi. Per ulteriori informazioni sull'utilizzo dell'SDK Vertex AI per Python con i modelli multimodali Gemini, consulta Introduzione alle classi multimodali nell'SDK Vertex AI per Python.

Python

Per scoprire come installare o aggiornare l'SDK Vertex AI per Python, consulta Installare l'SDK Vertex AI per Python. Per saperne di più, consulta la documentazione di riferimento dell'API Python.

import vertexai

from vertexai.generative_models import (
    Content,
    FunctionDeclaration,
    GenerationConfig,
    GenerativeModel,
    Part,
    Tool,
)

# TODO(developer): Update & uncomment below line
# PROJECT_ID = "your-project-id"

# Initialize Vertex AI
vertexai.init(project=PROJECT_ID, location="us-central1")

# Initialize Gemini model
model = GenerativeModel("gemini-1.5-flash-002")

# Define the user's prompt in a Content object that we can reuse in model calls
user_prompt_content = Content(
    role="user",
    parts=[
        Part.from_text("What is the weather like in Boston?"),
    ],
)

# Specify a function declaration and parameters for an API request
function_name = "get_current_weather"
get_current_weather_func = FunctionDeclaration(
    name=function_name,
    description="Get the current weather in a given location",
    # Function parameters are specified in JSON schema format
    parameters={
        "type": "object",
        "properties": {"location": {"type": "string", "description": "Location"}},
    },
)

# Define a tool that includes the above get_current_weather_func
weather_tool = Tool(
    function_declarations=[get_current_weather_func],
)

# Send the prompt and instruct the model to generate content using the Tool that you just created
response = model.generate_content(
    user_prompt_content,
    generation_config=GenerationConfig(temperature=0),
    tools=[weather_tool],
)
function_call = response.candidates[0].function_calls[0]
print(function_call)

# Check the function name that the model responded with, and make an API call to an external system
if function_call.name == function_name:
    # Extract the arguments to use in your API call
    location = function_call.args["location"]  # noqa: F841

    # Here you can use your preferred method to make an API request to fetch the current weather, for example:
    # api_response = requests.post(weather_api_url, data={"location": location})

    # In this example, we'll use synthetic data to simulate a response payload from an external API
    api_response = """{ "location": "Boston, MA", "temperature": 38, "description": "Partly Cloudy",
                    "icon": "partly-cloudy", "humidity": 65, "wind": { "speed": 10, "direction": "NW" } }"""

# Return the API response to Gemini so it can generate a model response or request another function call
response = model.generate_content(
    [
        user_prompt_content,  # User prompt
        response.candidates[0].content,  # Function call response
        Content(
            parts=[
                Part.from_function_response(
                    name=function_name,
                    response={
                        "content": api_response,  # Return the API response to Gemini
                    },
                ),
            ],
        ),
    ],
    tools=[weather_tool],
)

# Get the model response
print(response.text)
# Example response:
# The weather in Boston is partly cloudy with a temperature of 38 degrees Fahrenheit.
# The humidity is 65% and the wind is blowing from the northwest at 10 mph.

C#

Questo esempio mostra uno scenario di testo con una funzione e un prompt.

C#

Prima di provare questo esempio, segui le istruzioni di configurazione C# riportate nella guida rapida all'utilizzo delle librerie client di Vertex AI. Per ulteriori informazioni, consulta la documentazione di riferimento dell'API C# di Vertex AI.

Per autenticarti in Vertex AI, configura le Credenziali predefinite dell'applicazione. Per ulteriori informazioni, consulta Configurare l'autenticazione per un ambiente di sviluppo locale.


using Google.Cloud.AIPlatform.V1;
using System;
using System.Threading.Tasks;
using Type = Google.Cloud.AIPlatform.V1.Type;
using Value = Google.Protobuf.WellKnownTypes.Value;

public class FunctionCalling
{
    public async Task<string> GenerateFunctionCall(
        string projectId = "your-project-id",
        string location = "us-central1",
        string publisher = "google",
        string model = "gemini-1.5-flash-001")
    {
        var predictionServiceClient = new PredictionServiceClientBuilder
        {
            Endpoint = $"{location}-aiplatform.googleapis.com"
        }.Build();

        // Define the user's prompt in a Content object that we can reuse in
        // model calls
        var userPromptContent = new Content
        {
            Role = "USER",
            Parts =
            {
                new Part { Text = "What is the weather like in Boston?" }
            }
        };

        // Specify a function declaration and parameters for an API request
        var functionName = "get_current_weather";
        var getCurrentWeatherFunc = new FunctionDeclaration
        {
            Name = functionName,
            Description = "Get the current weather in a given location",
            Parameters = new OpenApiSchema
            {
                Type = Type.Object,
                Properties =
                {
                    ["location"] = new()
                    {
                        Type = Type.String,
                        Description = "Get the current weather in a given location"
                    },
                    ["unit"] = new()
                    {
                        Type = Type.String,
                        Description = "The unit of measurement for the temperature",
                        Enum = {"celsius", "fahrenheit"}
                    }
                },
                Required = { "location" }
            }
        };

        // Send the prompt and instruct the model to generate content using the tool that you just created
        var generateContentRequest = new GenerateContentRequest
        {
            Model = $"projects/{projectId}/locations/{location}/publishers/{publisher}/models/{model}",
            GenerationConfig = new GenerationConfig
            {
                Temperature = 0f
            },
            Contents =
            {
                userPromptContent
            },
            Tools =
            {
                new Tool
                {
                    FunctionDeclarations = { getCurrentWeatherFunc }
                }
            }
        };

        GenerateContentResponse response = await predictionServiceClient.GenerateContentAsync(generateContentRequest);

        var functionCall = response.Candidates[0].Content.Parts[0].FunctionCall;
        Console.WriteLine(functionCall);

        string apiResponse = "";

        // Check the function name that the model responded with, and make an API call to an external system
        if (functionCall.Name == functionName)
        {
            // Extract the arguments to use in your API call
            string locationCity = functionCall.Args.Fields["location"].StringValue;

            // Here you can use your preferred method to make an API request to
            // fetch the current weather

            // In this example, we'll use synthetic data to simulate a response
            // payload from an external API
            apiResponse = @"{ ""location"": ""Boston, MA"",
                    ""temperature"": 38, ""description"": ""Partly Cloudy""}";
        }

        // Return the API response to Gemini so it can generate a model response or request another function call
        generateContentRequest = new GenerateContentRequest
        {
            Model = $"projects/{projectId}/locations/{location}/publishers/{publisher}/models/{model}",
            Contents =
            {
                userPromptContent, // User prompt
                response.Candidates[0].Content, // Function call response,
                new Content
                {
                    Parts =
                    {
                        new Part
                        {
                            FunctionResponse = new()
                            {
                                Name = functionName,
                                Response = new()
                                {
                                    Fields =
                                    {
                                        { "content", new Value { StringValue = apiResponse } }
                                    }
                                }
                            }
                        }
                    }
                }
            },
            Tools =
            {
                new Tool
                {
                    FunctionDeclarations = { getCurrentWeatherFunc }
                }
            }
        };

        response = await predictionServiceClient.GenerateContentAsync(generateContentRequest);

        string responseText = response.Candidates[0].Content.Parts[0].Text;
        Console.WriteLine(responseText);

        return responseText;
    }
}

Node.js

Questo esempio mostra uno scenario di testo con una funzione e un prompt.

Node.js

Prima di provare questo esempio, segui le istruzioni di configurazione Node.js riportate nella guida rapida all'utilizzo delle librerie client di Vertex AI. Per ulteriori informazioni, consulta la documentazione di riferimento dell'API Node.js di Vertex AI.

Per autenticarti in Vertex AI, configura le Credenziali predefinite dell'applicazione. Per ulteriori informazioni, consulta Configurare l'autenticazione per un ambiente di sviluppo locale.

const {
  VertexAI,
  FunctionDeclarationSchemaType,
} = require('@google-cloud/vertexai');

const functionDeclarations = [
  {
    function_declarations: [
      {
        name: 'get_current_weather',
        description: 'get weather in a given location',
        parameters: {
          type: FunctionDeclarationSchemaType.OBJECT,
          properties: {
            location: {type: FunctionDeclarationSchemaType.STRING},
            unit: {
              type: FunctionDeclarationSchemaType.STRING,
              enum: ['celsius', 'fahrenheit'],
            },
          },
          required: ['location'],
        },
      },
    ],
  },
];

const functionResponseParts = [
  {
    functionResponse: {
      name: 'get_current_weather',
      response: {name: 'get_current_weather', content: {weather: 'super nice'}},
    },
  },
];

/**
 * TODO(developer): Update these variables before running the sample.
 */
async function functionCallingStreamContent(
  projectId = 'PROJECT_ID',
  location = 'us-central1',
  model = 'gemini-1.5-flash-001'
) {
  // Initialize Vertex with your Cloud project and location
  const vertexAI = new VertexAI({project: projectId, location: location});

  // Instantiate the model
  const generativeModel = vertexAI.getGenerativeModel({
    model: model,
  });

  const request = {
    contents: [
      {role: 'user', parts: [{text: 'What is the weather in Boston?'}]},
      {
        role: 'ASSISTANT',
        parts: [
          {
            functionCall: {
              name: 'get_current_weather',
              args: {location: 'Boston'},
            },
          },
        ],
      },
      {role: 'USER', parts: functionResponseParts},
    ],
    tools: functionDeclarations,
  };
  const streamingResp = await generativeModel.generateContentStream(request);
  for await (const item of streamingResp.stream) {
    console.log(item.candidates[0].content.parts[0].text);
  }
}

REST

Questo esempio mostra uno scenario di testo con tre funzioni e un prompt.

In questo esempio, chiami il modello di AI generativa due volte.

  • Nella prima chiamata, fornisci al modello il prompt e le dichiarazioni di funzione.
  • Nella seconda chiamata, fornisci al modello la risposta dell'API.

Prima richiesta di modello

La richiesta deve definire un prompt nel parametro text. Questo esempio definisce quanto segue prompt: "Quali cinema a Mountain View proiettano il film Barbie?".

La richiesta deve anche definire uno strumento (tools) con un insieme di dichiarazioni di funzione (functionDeclarations). Queste dichiarazioni di funzione devono essere specificate in un formato compatibile con lo schema OpenAPI. Questo esempio definisce le seguenti funzioni:

  • find_movies trova i titoli dei film in programmazione nelle sale.
  • find_theatres trova i cinema in base alla località.
  • get_showtimes trova gli orari di inizio dei film in programmazione in un cinema specifico.

Per scoprire di più sui parametri della richiesta del modello, consulta API Gemini.

Sostituisci my-project con il nome del tuo progetto Google Cloud.

Prima richiesta di modello

PROJECT_ID=my-project
MODEL_ID=gemini-1.0-pro
API=streamGenerateContent
curl -X POST -H "Authorization: Bearer $(gcloud auth print-access-token)" -H "Content-Type: application/json"  https://us-central1-aiplatform.googleapis.com/v1/projects/${PROJECT_ID}/locations/us-central1/publishers/google/models/${MODEL_ID}:${API} -d '{
"contents": {
  "role": "user",
  "parts": {
    "text": "Which theaters in Mountain View show the Barbie movie?"
  }
},
"tools": [
  {
    "function_declarations": [
      {
        "name": "find_movies",
        "description": "find movie titles currently playing in theaters based on any description, genre, title words, etc.",
        "parameters": {
          "type": "object",
          "properties": {
            "location": {
              "type": "string",
              "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
            },
            "description": {
              "type": "string",
              "description": "Any kind of description including category or genre, title words, attributes, etc."
            }
          },
          "required": [
            "description"
          ]
        }
      },
      {
        "name": "find_theaters",
        "description": "find theaters based on location and optionally movie title which are is currently playing in theaters",
        "parameters": {
          "type": "object",
          "properties": {
            "location": {
              "type": "string",
              "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
            },
            "movie": {
              "type": "string",
              "description": "Any movie title"
            }
          },
          "required": [
            "location"
          ]
        }
      },
      {
        "name": "get_showtimes",
        "description": "Find the start times for movies playing in a specific theater",
        "parameters": {
          "type": "object",
          "properties": {
            "location": {
              "type": "string",
              "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
            },
            "movie": {
              "type": "string",
              "description": "Any movie title"
            },
            "theater": {
              "type": "string",
              "description": "Name of the theater"
            },
            "date": {
              "type": "string",
              "description": "Date for requested showtime"
            }
          },
          "required": [
            "location",
            "movie",
            "theater",
            "date"
          ]
        }
      }
    ]
  }
]
}'
  

Per il prompt "Quali cinema a Mountain View proiettano il film Barbie?", il modello potrebbe restituire la funzione find_theatres con i parametri Barbie e Mountain View, CA.

Risposta alla prima richiesta di modello

[{
"candidates": [
  {
    "content": {
      "parts": [
        {
          "functionCall": {
            "name": "find_theaters",
            "args": {
              "movie": "Barbie",
              "location": "Mountain View, CA"
            }
          }
        }
      ]
    },
    "finishReason": "STOP",
    "safetyRatings": [
      {
        "category": "HARM_CATEGORY_HARASSMENT",
        "probability": "NEGLIGIBLE"
      },
      {
        "category": "HARM_CATEGORY_HATE_SPEECH",
        "probability": "NEGLIGIBLE"
      },
      {
        "category": "HARM_CATEGORY_SEXUALLY_EXPLICIT",
        "probability": "NEGLIGIBLE"
      },
      {
        "category": "HARM_CATEGORY_DANGEROUS_CONTENT",
        "probability": "NEGLIGIBLE"
      }
    ]
  }
],
"usageMetadata": {
  "promptTokenCount": 9,
  "totalTokenCount": 9
}
}]
  

Seconda richiesta di modello

Questo esempio utilizza dati sintetici anziché chiamare l'API esterna. Esistono due risultati, ciascuno con due parametri (name e address):

  1. name: AMC Mountain View 16, address: 2000 W El Camino Real, Mountain View, CA 94040
  2. name: Regal Edwards 14, address: 245 Castro St, Mountain View, CA 94040

Sostituisci my-project con il nome del tuo progetto Google Cloud.

Seconda richiesta di modello

PROJECT_ID=my-project
MODEL_ID=gemini-1.0-pro
API=streamGenerateContent
curl -X POST -H "Authorization: Bearer $(gcloud auth print-access-token)" -H "Content-Type: application/json"  https://us-central1-aiplatform.googleapis.com/v1/projects/${PROJECT_ID}/locations/us-central1/publishers/google/models/${MODEL_ID}:${API} -d '{
"contents": [{
  "role": "user",
  "parts": [{
    "text": "Which theaters in Mountain View show the Barbie movie?"
  }]
}, {
  "role": "model",
  "parts": [{
    "functionCall": {
      "name": "find_theaters",
      "args": {
        "location": "Mountain View, CA",
        "movie": "Barbie"
      }
    }
  }]
}, {
  "parts": [{
    "functionResponse": {
      "name": "find_theaters",
      "response": {
        "name": "find_theaters",
        "content": {
          "movie": "Barbie",
          "theaters": [{
            "name": "AMC Mountain View 16",
            "address": "2000 W El Camino Real, Mountain View, CA 94040"
          }, {
            "name": "Regal Edwards 14",
            "address": "245 Castro St, Mountain View, CA 94040"
          }]
        }
      }
    }
  }]
}],
"tools": [{
  "functionDeclarations": [{
    "name": "find_movies",
    "description": "find movie titles currently playing in theaters based on any description, genre, title words, etc.",
    "parameters": {
      "type": "OBJECT",
      "properties": {
        "location": {
          "type": "STRING",
          "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
        },
        "description": {
          "type": "STRING",
          "description": "Any kind of description including category or genre, title words, attributes, etc."
        }
      },
      "required": ["description"]
    }
  }, {
    "name": "find_theaters",
    "description": "find theaters based on location and optionally movie title which are is currently playing in theaters",
    "parameters": {
      "type": "OBJECT",
      "properties": {
        "location": {
          "type": "STRING",
          "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
        },
        "movie": {
          "type": "STRING",
          "description": "Any movie title"
        }
      },
      "required": ["location"]
    }
  }, {
    "name": "get_showtimes",
    "description": "Find the start times for movies playing in a specific theater",
    "parameters": {
      "type": "OBJECT",
      "properties": {
        "location": {
          "type": "STRING",
          "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
        },
        "movie": {
          "type": "STRING",
          "description": "Any movie title"
        },
        "theater": {
          "type": "STRING",
          "description": "Name of the theater"
        },
        "date": {
          "type": "STRING",
          "description": "Date for requested showtime"
        }
      },
      "required": ["location", "movie", "theater", "date"]
    }
  }]
}]
}'
  

La risposta del modello potrebbe essere simile alla seguente:

Risposta alla richiesta del secondo modello

{
"candidates": [
  {
    "content": {
      "parts": [
        {
          "text": " OK. Barbie is showing in two theaters in Mountain View, CA: AMC Mountain View 16 and Regal Edwards 14."
        }
      ]
    }
  }
],
"usageMetadata": {
  "promptTokenCount": 9,
  "candidatesTokenCount": 27,
  "totalTokenCount": 36
}
}
  

Esempi di chat

Puoi utilizzare le chiamate di funzione per supportare una sessione di chat. Le sessioni di chat sono utili in scenari di conversazione in formato libero, in cui è probabile che un utente ponga domande di seguito.

Se utilizzi le chiamate di funzione nel contesto di una sessione di chat, la sessione memorizza il contesto per te e lo include in ogni richiesta del modello. Vertex AI archivia la cronologia dell'interazione lato client.

Python

Questo esempio mostra uno scenario di chat con due funzioni e due prompt sequenziali. Utilizza la classe GenerativeModel e i relativi metodi. Per maggiori informazioni sull'utilizzo dell'SDK Vertex AI per Python con i modelli multimodali, consulta Introduzione alle classi multimodali nell'SDK Vertex AI per Python.

Per scoprire come installare o aggiornare Python, consulta Installare l'SDK Vertex AI per Python. Per saperne di più, consulta la documentazione di riferimento dell'API Python.

import vertexai

from vertexai.generative_models import (
    FunctionDeclaration,
    GenerationConfig,
    GenerativeModel,
    Part,
    Tool,
)

# TODO(developer): Update & uncomment below line
# PROJECT_ID = "your-project-id"

# Initialize Vertex AI
vertexai.init(project=PROJECT_ID, location="us-central1")

# Specify a function declaration and parameters for an API request
get_product_sku = "get_product_sku"
get_product_sku_func = FunctionDeclaration(
    name=get_product_sku,
    description="Get the SKU for a product",
    # Function parameters are specified in OpenAPI JSON schema format
    parameters={
        "type": "object",
        "properties": {
            "product_name": {"type": "string", "description": "Product name"}
        },
    },
)

# Specify another function declaration and parameters for an API request
get_store_location_func = FunctionDeclaration(
    name="get_store_location",
    description="Get the location of the closest store",
    # Function parameters are specified in JSON schema format
    parameters={
        "type": "object",
        "properties": {"location": {"type": "string", "description": "Location"}},
    },
)

# Define a tool that includes the above functions
retail_tool = Tool(
    function_declarations=[
        get_product_sku_func,
        get_store_location_func,
    ],
)

# Initialize Gemini model
model = GenerativeModel(
    model_name="gemini-1.5-flash-001",
    generation_config=GenerationConfig(temperature=0),
    tools=[retail_tool],
)

# Start a chat session
chat = model.start_chat()

# Send a prompt for the first conversation turn that should invoke the get_product_sku function
response = chat.send_message("Do you have the Pixel 8 Pro in stock?")

function_call = response.candidates[0].function_calls[0]
print(function_call)

# Check the function name that the model responded with, and make an API call to an external system
if function_call.name == get_product_sku:
    # Extract the arguments to use in your API call
    product_name = function_call.args["product_name"]  # noqa: F841

    # Here you can use your preferred method to make an API request to retrieve the product SKU, as in:
    # api_response = requests.post(product_api_url, data={"product_name": product_name})

    # In this example, we'll use synthetic data to simulate a response payload from an external API
    api_response = {"sku": "GA04834-US", "in_stock": "Yes"}

# Return the API response to Gemini, so it can generate a model response or request another function call
response = chat.send_message(
    Part.from_function_response(
        name=get_product_sku,
        response={
            "content": api_response,
        },
    ),
)
# Extract the text from the model response
print(response.text)

# Send a prompt for the second conversation turn that should invoke the get_store_location function
response = chat.send_message(
    "Is there a store in Mountain View, CA that I can visit to try it out?"
)

function_call = response.candidates[0].function_calls[0]
print(function_call)

# Check the function name that the model responded with, and make an API call to an external system
if function_call.name == "get_store_location":
    # Extract the arguments to use in your API call
    location = function_call.args["location"]  # noqa: F841

    # Here you can use your preferred method to make an API request to retrieve store location closest to the user, as in:
    # api_response = requests.post(store_api_url, data={"location": location})

    # In this example, we'll use synthetic data to simulate a response payload from an external API
    api_response = {"store": "2000 N Shoreline Blvd, Mountain View, CA 94043, US"}

# Return the API response to Gemini, so it can generate a model response or request another function call
response = chat.send_message(
    Part.from_function_response(
        name="get_store_location",
        response={
            "content": api_response,
        },
    ),
)

# Extract the text from the model response
print(response.text)
# Example response:
# name: "get_product_sku"
# args {
#   fields { key: "product_name" value {string_value: "Pixel 8 Pro" }
#   }
# }
# Yes, we have the Pixel 8 Pro in stock.
# name: "get_store_location"
# args {
#   fields { key: "location" value { string_value: "Mountain View, CA" }
#   }
# }
# Yes, there is a store located at 2000 N Shoreline Blvd, Mountain View, CA 94043, US.

Java

Prima di provare questo esempio, segui le istruzioni di configurazione Java riportate nella guida rapida all'utilizzo delle librerie client di Vertex AI. Per ulteriori informazioni, consulta la documentazione di riferimento dell'API Java di Vertex AI.

Per autenticarti in Vertex AI, configura le Credenziali predefinite dell'applicazione. Per ulteriori informazioni, consulta Configurare l'autenticazione per un ambiente di sviluppo locale.

import com.google.cloud.vertexai.VertexAI;
import com.google.cloud.vertexai.api.Content;
import com.google.cloud.vertexai.api.FunctionDeclaration;
import com.google.cloud.vertexai.api.GenerateContentResponse;
import com.google.cloud.vertexai.api.Schema;
import com.google.cloud.vertexai.api.Tool;
import com.google.cloud.vertexai.api.Type;
import com.google.cloud.vertexai.generativeai.ChatSession;
import com.google.cloud.vertexai.generativeai.ContentMaker;
import com.google.cloud.vertexai.generativeai.GenerativeModel;
import com.google.cloud.vertexai.generativeai.PartMaker;
import com.google.cloud.vertexai.generativeai.ResponseHandler;
import java.io.IOException;
import java.util.Arrays;
import java.util.Collections;

public class FunctionCalling {
  public static void main(String[] args) throws IOException {
    // TODO(developer): Replace these variables before running the sample.
    String projectId = "your-google-cloud-project-id";
    String location = "us-central1";
    String modelName = "gemini-1.5-flash-001";

    String promptText = "What's the weather like in Paris?";

    whatsTheWeatherLike(projectId, location, modelName, promptText);
  }

  // A request involving the interaction with an external tool
  public static String whatsTheWeatherLike(String projectId, String location,
                                           String modelName, String promptText)
      throws IOException {
    // Initialize client that will be used to send requests.
    // This client only needs to be created once, and can be reused for multiple requests.
    try (VertexAI vertexAI = new VertexAI(projectId, location)) {

      FunctionDeclaration functionDeclaration = FunctionDeclaration.newBuilder()
          .setName("getCurrentWeather")
          .setDescription("Get the current weather in a given location")
          .setParameters(
              Schema.newBuilder()
                  .setType(Type.OBJECT)
                  .putProperties("location", Schema.newBuilder()
                      .setType(Type.STRING)
                      .setDescription("location")
                      .build()
                  )
                  .addRequired("location")
                  .build()
          )
          .build();

      System.out.println("Function declaration:");
      System.out.println(functionDeclaration);

      // Add the function to a "tool"
      Tool tool = Tool.newBuilder()
          .addFunctionDeclarations(functionDeclaration)
          .build();

      // Start a chat session from a model, with the use of the declared function.
      GenerativeModel model = new GenerativeModel(modelName, vertexAI)
          .withTools(Arrays.asList(tool));
      ChatSession chat = model.startChat();

      System.out.println(String.format("Ask the question: %s", promptText));
      GenerateContentResponse response = chat.sendMessage(promptText);

      // The model will most likely return a function call to the declared
      // function `getCurrentWeather` with "Paris" as the value for the
      // argument `location`.
      System.out.println("\nPrint response: ");
      System.out.println(ResponseHandler.getContent(response));

      // Provide an answer to the model so that it knows what the result
      // of a "function call" is.
      Content content =
          ContentMaker.fromMultiModalData(
              PartMaker.fromFunctionResponse(
                  "getCurrentWeather",
                  Collections.singletonMap("currentWeather", "sunny")));
      System.out.println("Provide the function response: ");
      System.out.println(content);
      response = chat.sendMessage(content);

      // See what the model replies now
      System.out.println("Print response: ");
      String finalAnswer = ResponseHandler.getText(response);
      System.out.println(finalAnswer);

      return finalAnswer;
    }
  }
}

Go

Prima di provare questo esempio, segui le istruzioni di configurazione Go riportate nella guida rapida all'utilizzo delle librerie client di Vertex AI. Per ulteriori informazioni, consulta la documentazione di riferimento dell'API Go di Vertex AI.

Per autenticarti in Vertex AI, configura le Credenziali predefinite dell'applicazione. Per ulteriori informazioni, consulta Configurare l'autenticazione per un ambiente di sviluppo locale.

import (
	"context"
	"encoding/json"
	"errors"
	"fmt"
	"io"

	"cloud.google.com/go/vertexai/genai"
)

// functionCallsChat opens a chat session and sends 4 messages to the model:
// - convert a first text question into a structured function call request
// - convert the first structured function call response into natural language
// - convert a second text question into a structured function call request
// - convert the second structured function call response into natural language
func functionCallsChat(w io.Writer, projectID, location, modelName string) error {
	// location := "us-central1"
	// modelName := "gemini-1.5-flash-001"
	ctx := context.Background()
	client, err := genai.NewClient(ctx, projectID, location)
	if err != nil {
		return fmt.Errorf("unable to create client: %w", err)
	}
	defer client.Close()

	model := client.GenerativeModel(modelName)

	// Build an OpenAPI schema, in memory
	paramsProduct := &genai.Schema{
		Type: genai.TypeObject,
		Properties: map[string]*genai.Schema{
			"productName": {
				Type:        genai.TypeString,
				Description: "Product name",
			},
		},
	}
	fundeclProductInfo := &genai.FunctionDeclaration{
		Name:        "getProductSku",
		Description: "Get the SKU for a product",
		Parameters:  paramsProduct,
	}
	paramsStore := &genai.Schema{
		Type: genai.TypeObject,
		Properties: map[string]*genai.Schema{
			"location": {
				Type:        genai.TypeString,
				Description: "Location",
			},
		},
	}
	fundeclStoreLocation := &genai.FunctionDeclaration{
		Name:        "getStoreLocation",
		Description: "Get the location of the closest store",
		Parameters:  paramsStore,
	}
	model.Tools = []*genai.Tool{
		{FunctionDeclarations: []*genai.FunctionDeclaration{
			fundeclProductInfo,
			fundeclStoreLocation,
		}},
	}
	model.SetTemperature(0.0)

	chat := model.StartChat()

	// Send a prompt for the first conversation turn that should invoke the getProductSku function
	prompt := "Do you have the Pixel 8 Pro in stock?"
	fmt.Fprintf(w, "Question: %s\n", prompt)
	resp, err := chat.SendMessage(ctx, genai.Text(prompt))
	if err != nil {
		return err
	}
	if len(resp.Candidates) == 0 ||
		len(resp.Candidates[0].Content.Parts) == 0 {
		return errors.New("empty response from model")
	}

	// The model has returned a function call to the declared function `getProductSku`
	// with a value for the argument `productName`.
	jsondata, err := json.MarshalIndent(resp.Candidates[0].Content.Parts[0], "\t", "  ")
	if err != nil {
		return fmt.Errorf("json.MarshalIndent: %w", err)
	}
	fmt.Fprintf(w, "function call generated by the model:\n\t%s\n", string(jsondata))

	// Create a function call response, to simulate the result of a call to a
	// real service
	funresp := &genai.FunctionResponse{
		Name: "getProductSku",
		Response: map[string]any{
			"sku":      "GA04834-US",
			"in_stock": "yes",
		},
	}
	jsondata, err = json.MarshalIndent(funresp, "\t", "  ")
	if err != nil {
		return fmt.Errorf("json.MarshalIndent: %w", err)
	}
	fmt.Fprintf(w, "function call response sent to the model:\n\t%s\n\n", string(jsondata))

	// And provide the function call response to the model
	resp, err = chat.SendMessage(ctx, funresp)
	if err != nil {
		return err
	}
	if len(resp.Candidates) == 0 ||
		len(resp.Candidates[0].Content.Parts) == 0 {
		return errors.New("empty response from model")
	}

	// The model has taken the function call response as input, and has
	// reformulated the response to the user.
	jsondata, err = json.MarshalIndent(resp.Candidates[0].Content.Parts[0], "\t", "  ")
	if err != nil {
		return fmt.Errorf("json.MarshalIndent: %w", err)
	}
	fmt.Fprintf(w, "Answer generated by the model:\n\t%s\n\n", string(jsondata))

	// Send a prompt for the second conversation turn that should invoke the getStoreLocation function
	prompt2 := "Is there a store in Mountain View, CA that I can visit to try it out?"
	fmt.Fprintf(w, "Question: %s\n", prompt)

	resp, err = chat.SendMessage(ctx, genai.Text(prompt2))
	if err != nil {
		return err
	}
	if len(resp.Candidates) == 0 ||
		len(resp.Candidates[0].Content.Parts) == 0 {
		return errors.New("empty response from model")
	}

	// The model has returned a function call to the declared function `getStoreLocation`
	// with a value for the argument `store`.
	jsondata, err = json.MarshalIndent(resp.Candidates[0].Content.Parts[0], "\t", "  ")
	if err != nil {
		return fmt.Errorf("json.MarshalIndent: %w", err)
	}
	fmt.Fprintf(w, "function call generated by the model:\n\t%s\n", string(jsondata))

	// Create a function call response, to simulate the result of a call to a
	// real service
	funresp = &genai.FunctionResponse{
		Name: "getStoreLocation",
		Response: map[string]any{
			"store": "2000 N Shoreline Blvd, Mountain View, CA 94043, US",
		},
	}
	jsondata, err = json.MarshalIndent(funresp, "\t", "  ")
	if err != nil {
		return fmt.Errorf("json.MarshalIndent: %w", err)
	}
	fmt.Fprintf(w, "function call response sent to the model:\n\t%s\n\n", string(jsondata))

	// And provide the function call response to the model
	resp, err = chat.SendMessage(ctx, funresp)
	if err != nil {
		return err
	}
	if len(resp.Candidates) == 0 ||
		len(resp.Candidates[0].Content.Parts) == 0 {
		return errors.New("empty response from model")
	}

	// The model has taken the function call response as input, and has
	// reformulated the response to the user.
	jsondata, err = json.MarshalIndent(resp.Candidates[0].Content.Parts[0], "\t", "  ")
	if err != nil {
		return fmt.Errorf("json.MarshalIndent: %w", err)
	}
	fmt.Fprintf(w, "Answer generated by the model:\n\t%s\n\n", string(jsondata))
	return nil
}

Node.js

Prima di provare questo esempio, segui le istruzioni di configurazione Node.js riportate nella guida rapida all'utilizzo delle librerie client di Vertex AI. Per ulteriori informazioni, consulta la documentazione di riferimento dell'API Node.js di Vertex AI.

Per autenticarti in Vertex AI, configura le Credenziali predefinite dell'applicazione. Per ulteriori informazioni, consulta Configurare l'autenticazione per un ambiente di sviluppo locale.

const {
  VertexAI,
  FunctionDeclarationSchemaType,
} = require('@google-cloud/vertexai');

const functionDeclarations = [
  {
    function_declarations: [
      {
        name: 'get_current_weather',
        description: 'get weather in a given location',
        parameters: {
          type: FunctionDeclarationSchemaType.OBJECT,
          properties: {
            location: {type: FunctionDeclarationSchemaType.STRING},
            unit: {
              type: FunctionDeclarationSchemaType.STRING,
              enum: ['celsius', 'fahrenheit'],
            },
          },
          required: ['location'],
        },
      },
    ],
  },
];

const functionResponseParts = [
  {
    functionResponse: {
      name: 'get_current_weather',
      response: {name: 'get_current_weather', content: {weather: 'super nice'}},
    },
  },
];

/**
 * TODO(developer): Update these variables before running the sample.
 */
async function functionCallingStreamChat(
  projectId = 'PROJECT_ID',
  location = 'us-central1',
  model = 'gemini-1.5-flash-001'
) {
  // Initialize Vertex with your Cloud project and location
  const vertexAI = new VertexAI({project: projectId, location: location});

  // Instantiate the model
  const generativeModel = vertexAI.getGenerativeModel({
    model: model,
  });

  // Create a chat session and pass your function declarations
  const chat = generativeModel.startChat({
    tools: functionDeclarations,
  });

  const chatInput1 = 'What is the weather in Boston?';

  // This should include a functionCall response from the model
  const result1 = await chat.sendMessageStream(chatInput1);
  for await (const item of result1.stream) {
    console.log(item.candidates[0]);
  }
  await result1.response;

  // Send a follow up message with a FunctionResponse
  const result2 = await chat.sendMessageStream(functionResponseParts);
  for await (const item of result2.stream) {
    console.log(item.candidates[0]);
  }

  // This should include a text response from the model using the response content
  // provided above
  const response2 = await result2.response;
  console.log(response2.candidates[0].content.parts[0].text);
}

Esempio di chiamata di funzioni parallele

Per prompt come "Vorrei avere i dettagli meteo di New Delhi e San Francisco", il modello potrebbe proporre diverse chiamate di funzioni in parallelo. Per un elenco dei modelli che supportano le chiamate di funzioni parallele, consulta Modelli supportati.

REST

Questo esempio mostra uno scenario con una funzione get_current_weather. Il prompt dell'utente è "Vorrei i dettagli meteo di New Delhi e San Francisco". Il modello propone due chiamate di funzione get_current_weather parallele: una con il parametro New Delhi e l'altra con il parametro San Francisco.

Per scoprire di più sui parametri della richiesta del modello, consulta API Gemini.

{
"candidates": [
  {
    "content": {
      "role": "model",
      "parts": [
        {
          "functionCall": {
            "name": "get_current_weather",
            "args": {
              "location": "New Delhi"
            }
          }
        },
        {
          "functionCall": {
            "name": "get_current_weather",
            "args": {
              "location": "San Francisco"
            }
          }
        }
      ]
    },
    ...
  }
],
...
}

Il seguente comando mostra come puoi fornire l'output della funzione al modello. Sostituisci my-project con il nome del tuo progetto Google Cloud.

Richiesta del modello

PROJECT_ID=my-project
MODEL_ID=gemini-1.5-pro-002
VERSION="v1"
LOCATION="us-central1"
ENDPOINT=${LOCATION}-aiplatform.googleapis.com
API="generateContent"
curl -X POST -H "Authorization: Bearer $(gcloud auth print-access-token)" -H "Content-Type: application/json"  https://${ENDPOINT}/${VERSION}/projects/${PROJECT_ID}/locations/${LOCATION}/publishers/google/models/${MODEL_ID}:${API} -d '{
"contents": [
    {
        "role": "user",
        "parts": {
            "text": "What is difference in temperature in New Delhi and San Francisco?"
        }
    },
    {
        "role": "model",
        "parts": [
            {
                "functionCall": {
                    "name": "get_current_weather",
                    "args": {
                        "location": "New Delhi"
                    }
                }
            },
            {
                "functionCall": {
                    "name": "get_current_weather",
                    "args": {
                        "location": "San Francisco"
                    }
                }
            }
        ]
    },
    {
        "role": "user",
        "parts": [
            {
                "functionResponse": {
                    "name": "get_current_weather",
                    "response": {
                        "temperature": 30.5,
                        "unit": "C"
                    }
                }
            },
            {
                "functionResponse": {
                    "name": "get_current_weather",
                    "response": {
                        "temperature": 20,
                        "unit": "C"
                    }
                }
            }
        ]
    }
],
"tools": [
    {
        "function_declarations": [
            {
                "name": "get_current_weather",
                "description": "Get the current weather in a specific location",
                "parameters": {
                    "type": "object",
                    "properties": {
                        "location": {
                            "type": "string",
                            "description": "The city and state, e.g. San Francisco, CA or a zip code e.g. 95616"
                        }
                    },
                    "required": [
                        "location"
                    ]
                }
            }
        ]
    }
]
}'
  

La risposta in linguaggio naturale creata dal modello è simile alla seguente:

Risposta del modello

[
{
    "candidates": [
        {
            "content": {
                "parts": [
                    {
                        "text": "The temperature in New Delhi is 30.5C and the temperature in San Francisco is 20C. The difference is 10.5C. \n"
                    }
                ]
            },
            "finishReason": "STOP",
            ...
        }
    ]
    ...
}
]
  

Python

import vertexai

from vertexai.generative_models import (
    FunctionDeclaration,
    GenerativeModel,
    Part,
    Tool,
)

# TODO(developer): Update & uncomment below line
# PROJECT_ID = "your-project-id"

# Initialize Vertex AI
vertexai.init(project=PROJECT_ID, location="us-central1")

# Specify a function declaration and parameters for an API request
function_name = "get_current_weather"
get_current_weather_func = FunctionDeclaration(
    name=function_name,
    description="Get the current weather in a given location",
    parameters={
        "type": "object",
        "properties": {
            "location": {
                "type": "string",
                "description": "The location for which to get the weather. \
                  It can be a city name, a city name and state, or a zip code. \
                  Examples: 'San Francisco', 'San Francisco, CA', '95616', etc.",
            },
        },
    },
)

# In this example, we'll use synthetic data to simulate a response payload from an external API
def mock_weather_api_service(location: str) -> str:
    temperature = 25 if location == "San Francisco" else 35
    return f"""{{ "location": "{location}", "temperature": {temperature}, "unit": "C" }}"""

# Define a tool that includes the above function
tools = Tool(
    function_declarations=[get_current_weather_func],
)

# Initialize Gemini model
model = GenerativeModel(
    model_name="gemini-1.5-pro-002",
    tools=[tools],
)

# Start a chat session
chat_session = model.start_chat()
response = chat_session.send_message(
    "Get weather details in New Delhi and San Francisco?"
)

function_calls = response.candidates[0].function_calls
print("Suggested finction calls:\n", function_calls)

if function_calls:
    api_responses = []
    for func in function_calls:
        if func.name == function_name:
            api_responses.append(
                {
                    "content": mock_weather_api_service(
                        location=func.args["location"]
                    )
                }
            )

    # Return the API response to Gemini
    response = chat_session.send_message(
        [
            Part.from_function_response(
                name="get_current_weather",
                response=api_responses[0],
            ),
            Part.from_function_response(
                name="get_current_weather",
                response=api_responses[1],
            ),
        ],
    )

    print(response.text)
    # Example response:
    # The current weather in New Delhi is 35°C. The current weather in San Francisco is 25°C.

Best practice per le chiamate di funzioni

Nome funzione

Il nome della funzione deve iniziare con una lettera o un trattino basso e contenere solo caratteri a-z, A-Z, 0-9, trattini bassi, punti o trattini con una lunghezza massima di 64.

Descrizione della funzione

Scrivi le descrizioni delle funzioni in modo chiaro e dettagliato. Ad esempio, per una funzione book_flight_ticket:

  • Di seguito è riportato un esempio di una buona descrizione della funzione: book flight tickets after confirming users' specific requirements, such as time, departure, destination, party size and preferred airline
  • Di seguito è riportato un esempio di descrizione di una funzione sbagliata: book flight ticket

Parametri funzione

I nomi dei parametri di funzione e degli attributi nidificati devono iniziare con una lettera o un trattino basso e contenere solo caratteri a-z, A-Z, 0-9 o trattini bassi con una lunghezza massima di 64. Non utilizzare punti (.), trattini (-) o spazi nei nomi dei parametri delle funzioni e negli attributi nidificati. Utilizza invece i trattini bassi (_) o altri caratteri.

Descriptions

Scrivi descrizioni dei parametri chiare e dettagliate, inclusi dettagli come il formato o i valori preferiti. Ad esempio, per una funzione book_flight_ticket:

  • Di seguito è riportato un buon esempio di descrizione del parametro departure: Use the 3 char airport code to represent the airport. For example, SJC or SFO. Don't use the city name.
  • Di seguito è riportato un esempio errato di descrizione del parametro departure: the departure airport

Tipi

Se possibile, utilizza parametri fortemente tipizzati per ridurre le allucinazioni del modello. Ad esempio, se i valori del parametro provengono da un insieme finito, aggiungi un campo enum anziché inserire l'insieme di valori nella descrizione. Se il valore del parametro è sempre un numero intero, imposta il tipo su integer anziché number.

Istruzioni di sistema

Quando utilizzi funzioni con parametri di data, ora o posizione, includi la data, l'ora o i dati sulla posizione pertinenti (ad esempio città e paese) correnti nell'istruzione di sistema. In questo modo, il modello dispone del contesto necessario per elaborare la richiesta con precisione, anche se il prompt dell'utente manca di dettagli.

Comando dell'utente

Per risultati ottimali, anteponi al prompt dell'utente i seguenti dettagli:

  • Contesto aggiuntivo per il modello, ad esempio You are a flight API assistant to help with searching flights based on user preferences.
  • Dettagli o istruzioni su come e quando utilizzare le funzioni, ad esempio Don't make assumptions on the departure or destination airports. Always use a future date for the departure or destination time.
  • Istruzioni per porre domande di chiarimento se le query degli utenti sono ambigue, ad esempio Ask clarifying questions if not enough information is available.

Configurazione della generazione

Per il parametro temperatura, utilizza 0 o un altro valore basso. In questo modo, il modello genera risultati più affidabili e riduce le allucinazioni.

Invocazione dell'API

Se il modello propone l'invocazione di una funzione che invia un ordine, aggiorna un database o ha conseguenze significative, convalida la chiamata della funzione con l'utente prima di eseguirla.

Prezzi

I prezzi delle chiamate alle funzioni si basano sul numero di caratteri all'interno degli input e delle uscite di testo. Per scoprire di più, consulta la pagina relativa ai prezzi di Vertex AI.

Qui, l'input di testo (prompt) si riferisce al prompt dell'utente per il turno di conversazione corrente, alle dichiarazioni di funzione per il turno di conversazione corrente e alla cronologia della conversazione. La cronologia della conversazione include le query, le chiamate alle funzioni e le risposte alle funzioni dei turni di conversazione precedenti. Vertex AI tronca la cronologia della conversazione a 32.000 caratteri.

L'output di testo (risposta) si riferisce alle chiamate alle funzioni e alle risposte di testo per il turno di conversazione corrente.

Passaggi successivi