Google's function-calling documentation directly shows a Python configuration using model="gemini-3.8-flash": the model proposes only a function name and structured arguments, while the application validates and executes the function, then sends a function_result back through previous_interaction_id. This mechanism is suitable for connecting natural-language requests to controlled external data or APIs; it does not grant the application tool permissions.
Suitable tasks: Tasks that require the application to call an API, such as querying external data, creating charts, or making reservations; it is also suitable for calling multiple independent functions in parallel or chaining calls in dependency order.
Unsuitable tasks: Treating model output directly as a local command, payment, message-sending, or deletion operation; these actions must be controlled on the application side with allowlists, parameter validation, and human authorization.
Applicable model version: This article records only the gemini-3.8-flash explicitly written in the example on this page; do not treat model aliases or SDK mappings from other clients as the same evidence.
Applicable client, agent, or API: The Google Gemini API's Interactions API; the page says that the Interactions API has been officially released and recommends using it to access the latest features and models. Other SDKs require independent verification of field mappings.
Preview status: This function-calling page does not label this workflow as Preview; that does not mean it is simultaneously available across all SDK versions, regions, or third-party platforms, so a smoke test is still required before deployment.
The core fields from Google's Python example are retained below, using a read-only weather query as a safe starting point:
from google import genai
weather_function = {
"type": "function",
"name": "get_current_temperature",
"description": "Gets the current temperature for a given location.",
"parameters": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "The city name, e.g. San Francisco",
},
},
"required": ["location"],
},
}
client = genai.Client()
interaction = client.interactions.create(
model="gemini-3.8-flash",
input="What's the temperature in London?",
tools=[weather_function],
)
for step in interaction.steps:
if step.type == "function_call":
print(f"Function to call: {step.name}")
print(f"Arguments: {step.arguments}")The minimum declared fields are type="function", a unique name, a clear description, parameters (typically an object), and required, which consists of the names of required parameters. Parameter types, enumerations, and value ranges should match the real function; do not treat natural-language descriptions as access controls.
User input + tool declaration
↓
Interactions API returns function_call(name, arguments, call_id)
↓
Application validates arguments against an allowlist and executes its own function
↓
Returns the result as function_result
↓
Model generates the final user response or proposes another tool callThe official documentation makes clear that the model itself does not execute functions. The following example shows the complete application-side loop; replace the implementation of get_current_temperature with your own authorized API client:
import json
from google import genai
weather_function = {
"type": "function",
"name": "get_current_temperature",
"description": "Gets the current temperature for a given location.",
"parameters": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "The city name, e.g. San Francisco",
},
},
"required": ["location"],
},
}
def get_current_temperature(location: str) -> dict:
# Illustration only: production code should call an authorized weather service and handle timeouts/errors.
return {"location": location, "temperature_c": 18, "source": "example"}
client = genai.Client()
interaction = client.interactions.create(
model="gemini-3.8-flash",
input="What's the temperature in London?",
tools=[weather_function],
)
fc_step = next(s for s in interaction.steps if s.type == "function_call")
if fc_step.name != "get_current_temperature":
raise ValueError(f"Unexpected function: {fc_step.name}")
location = fc_step.arguments.get("location")
if not isinstance(location, str) or not location.strip():
raise ValueError("location must be a non-empty string")
result = get_current_temperature(location.strip())
final_interaction = client.interactions.create(
model="gemini-3.8-flash",
input=[{
"type": "function_result",
"name": fc_step.name,
"call_id": fc_step.id,
"result": [{"type": "text", "text": json.dumps(result)}],
}],
tools=[weather_function],
previous_interaction_id=interaction.id,
)
print(final_interaction.output_text)This user-input template is adapted to the function declaration above; it is not a system prompt claimed by Google:
Task: Answer the user's weather query.
Tool boundary:
- Request get_current_temperature only when a real-time temperature is needed.
- The parameters may contain only location, which must be a non-empty city name.
- Do not invent tool-returned values or claim that the tool has been executed; wait for the application to return function_result.
- If the tool fails, clearly state that the query failed and provide a retryable or human-handled next step.
User question:
[Enter the city and question]The documentation provides generation_config's tool_choice control modes: auto (the default, decided by the model), any (always predict a function call), and none (prohibit function calls). In multi-tool scenarios, allowed_tools can also narrow the set of functions that may be called:
generation_config = {
"tool_choice": {
"allowed_tools": {
"mode": "any",
"tools": ["get_current_temperature"],
},
},
}Use any only when the application truly wants the model to select a tool from a limited set; forcing a function call does not mean the arguments have passed business validation.
Configure Gemini API credentials in an isolated environment; keep keys only in environment variables or protected secret storage, and do not put them in prompts or the repository.
Run the read-only weather example with the exact model gemini-3.8-flash, recording whether a function_call is received, along with the function name, parameter types, and call_id.
On the application side, first check the function-name allowlist, then validate required fields, types, lengths, enumerations, and value ranges; do not call an external API when validation fails.
Set timeouts, error branches, and audit fields when executing the function; package only the minimally necessary result as function_result and return it through previous_interaction_id.
Check that the final answer distinguishes between “the model suggested a call,” “the application executed it,” and “the tool returned a result”; when a tool fails, preserve the error state instead of guessing data.
Also test a set of tasks that require parallel or combined calls; confirm that only side-effect-free, mutually independent functions run in parallel, while dependent calls return in sequence.
Add human confirmation and idempotency keys to tools that write, send, make payments, control devices, or delete; do not execute them without confirmation, even when the model emits a validly formatted call.
| Document location | What can be verified from Google | How this article uses it |
|---|---|---|
| Make a reservation / Get the weather / Create a chart examples | The Python examples set model to gemini-3.8-flash and pass function declarations through tools | Shows that the exact model and function-tool configuration used in this article come from the same official page |
| How function calling works | The flow is to define the declaration, call the model, have the application execute the function, and return the result; the model does not execute the function | Forms the four-step call chain and permission boundary |
| Function declaration | Explanations of the type, name, description, parameters, and required fields | Forms a tool contract that can be validated |
| Function-calling modes | auto, any, and none, along with configuration for restricting allowed_tools | Forms the tool-selection configuration |
| Function calling with thinking models / Using multiple tools | The Gemini 3 series can make parallel, combined, and multi-tool calls within an interaction; the SDK handles thinking signatures | Used only for orchestration test recommendations; does not infer success rates or permissions |
| Page header | The Interactions API has been officially released, and the page recommends using it to access the latest features and models | Explains the Preview boundary; does not extrapolate to all SDKs or platforms |
Register tools only for APIs, data, and devices that you own or are authorized to use; a tool declaration is not proof of authorization.
Function names and arguments must be validated against an application-side allowlist. The arguments returned by the model are untrusted input and must not be concatenated directly into SQL, shell commands, URLs, or payment requests.
For side-effecting operations such as making reservations, sending email, controlling devices, writing to a database, making payments, and deleting, first display the target, parameters, and risks, then wait for human confirmation; add idempotency keys and replay protection when necessary.
Tool results are also external input and may be stale, incorrect, or contain prompt injection. Return only the minimum fields needed to complete the task, while retaining the source, timestamp, and error state.
Store only necessary call metadata in logs; do not record API keys, authentication headers, email addresses, phone numbers, user tokens, or the complete original sensitive request.
Use previous_interaction_id only to associate interaction context; it must not be treated as a permission token. Access permissions, rate limits, auditing, and human takeover remain the application's responsibility.
Page examples do not constitute a production-quality or security guarantee. Before launch, validate tool selection, parameter rejection, timeouts, retries, cancellation, and human-takeover paths in a sandbox.
The documentation defines function calling as “a bridge between natural language and real-world actions and data” and emphasizes that executing functions is the application's responsibility. The key engineering implication is to treat the model's function_call as a structured request awaiting review, rather than as an external action that has already occurred.
Gemini 3.8 Flash