1. Введение
Обзор
Вы — разработчик в компании, занимающейся маркетингом в сфере туризма. Ваш отдел продаж решил, что ему нужно новое чат-приложение, чтобы не отставать от крупных компаний по бронированию и поиску. Они также слышали о генеративном ИИ , но пока не так много знают о нём. Другие отделы слышали об этой инициативе, и им интересно, как это может улучшить качество обслуживания клиентов.
Что ты будешь делать?
В этой лабораторной работе вы создадите чат-бота-помощника для путешествий, используя модель Gemini 2.5 Flash на базе Vertex AI .
Заявка должна:
- Помогает пользователям задавать вопросы о путешествиях, бронировать поездки и узнавать о местах, куда они планируют поехать.
- Предоставляет пользователям способы получения помощи по их конкретным планам поездок.
- Иметь возможность получать данные в режиме реального времени, например, о погоде, с помощью инструментов
Вы будете работать в предварительно настроенной среде Google Cloud, а именно в редакторе Cloud Shell Editor. Базовый веб-интерфейс приложения уже настроен, как и необходимые разрешения для доступа к Vertex AI. Это приложение создано с использованием Streamlit .
Чему вы научитесь
В этой лабораторной работе вы научитесь выполнять следующие задачи:
- Изучите платформу Vertex AI , чтобы определить доступные модели генеративного ИИ .
- Разработка в Cloud Shell Editor и терминале
- Используйте Gemini Code Assist для понимания кода.
- Используйте Vertex AI SDK на Python для отправки запросов и получения ответов от Gemini LLM .
- Применяйте базовые средства оперативной инженерии ( системные инструкции , параметры модели ) для настройки выходных данных Gemini LLM.
- Тестируйте и постоянно совершенствуйте чат-приложение на базе LLM , изменяя подсказки и параметры для улучшения ответов.
- Определите и используйте инструменты с моделью Gemini для обеспечения возможности вызова функций .
- Переработайте код, чтобы использовать сеанс чата с сохранением состояния — это лучшая практика для диалоговых приложений.
2. Настройка проекта
Аккаунт Google
Если у вас еще нет личного аккаунта Google, вам необходимо создать аккаунт Google .
Используйте личный аккаунт вместо рабочего или школьного.
Войдите в Google Cloud Console.
Войдите в Google Cloud Console, используя личный аккаунт Google.
Включить биллинг
Получите кредиты Google Cloud на сумму 5 долларов США (по желанию)
Для проведения этого семинара вам понадобится платёжный счёт с определённым балансом. Если вы планируете использовать собственный платёжный счёт, пропустите этот шаг.
- Нажмите на эту ссылку и войдите в систему, используя личный аккаунт Google. Вы увидите что-то вроде этого:

- Нажмите кнопку «НАЖМИТЕ ЗДЕСЬ, ЧТОБЫ ПОЛУЧИТЬ ДОСТУП К ВАШИМ КРЕДИТАМ». Это приведет вас на страницу для настройки вашего платежного профиля.

- Нажмите «Подтвердить».
Теперь вы подключены к пробной учетной записи Google Cloud Platform.

Настройте личный платежный аккаунт
Если вы настраиваете оплату с использованием кредитов Google Cloud, вы можете пропустить этот шаг.
Чтобы настроить персональную учетную запись для выставления счетов, перейдите сюда и включите выставление счетов в Cloud Console.
Некоторые заметки:
- Выполнение этой лабораторной работы обойдется менее чем в 1 доллар США в виде облачных ресурсов.
- Вы можете следовать инструкциям в конце этой лабораторной работы, чтобы удалить ресурсы и избежать дальнейших расходов.
- Новые пользователи имеют право на бесплатную пробную версию стоимостью 300 долларов США .
Создать проект (необязательно)
Если у вас нет текущего проекта, который вы хотели бы использовать для этого ярлыка, создайте новый проект здесь .
3. Откройте редактор Cloud Shell
- Нажмите эту ссылку, чтобы перейти непосредственно в редактор Cloud Shell.
- Если сегодня в какой-либо момент вам будет предложено авторизоваться, нажмите «Авторизовать» , чтобы продолжить.

- Если терминал не отображается внизу экрана, откройте его:
- Нажмите «Просмотр»
- Нажмите «Терминал»

- В терминале настройте свой проект с помощью этой команды:
gcloud config set project [PROJECT_ID]- Пример:
gcloud config set project lab-project-id-example - Если вы не можете вспомнить идентификатор своего проекта, вы можете перечислить все идентификаторы своих проектов с помощью:
gcloud projects list | awk '/PROJECT_ID/{print $2}'
- Пример:
- Вы должны увидеть это сообщение:
>aside negative Если вы видите `WARNING` и спрашиваете `Продолжить (Y/n)?`, вероятно, вы неправильно ввели идентификатор проекта. Нажмите `n`, нажмите `Enter` и попробуйте снова выполнить команду `gcloud config set project`. >Updated property [core/project].
4. Включите API
Чтобы использовать Vertex AI SDK и взаимодействовать с моделью Gemini, вам необходимо включить Vertex AI API в вашем проекте Google Cloud.
- В терминале включите API:
gcloud services enable \ aiplatform.googleapis.com
Введение в Vertex AI SDK для Python
Для взаимодействия с моделями, размещёнными в Vertex AI, из вашего приложения Python вам понадобится Vertex AI SDK для Python. Этот SDK упрощает процесс отправки запросов, указания параметров модели и получения ответов, избавляя от необходимости напрямую обрабатывать сложные вызовы API.
Подробную документацию по Vertex AI SDK для Python можно найти здесь: Введение в Vertex AI SDK для Python | Google Cloud .
5. Создайте виртуальную среду и установите зависимости.
Перед запуском любого проекта Python рекомендуется создать виртуальную среду. Это изолирует зависимости проекта, предотвращая конфликты с другими проектами или глобальными пакетами Python в системе.
- Создайте папку с именем
wanderbotдля хранения кода вашего приложения-помощника для путешествий. Запустите следующий код в терминале :mkdir wanderbot && cd wanderbot - Создайте и активируйте виртуальную среду:
Вы увидите префикс (uv venv --python 3.12 source .venv/bin/activatewanderbot) в строке терминала, указывающий на то, что виртуальная среда активна. Это будет выглядеть примерно так:
6. Создайте стартовые файлы для wanderbot
- Создайте и откройте новый файл
app.pyдля приложения. Запустите следующий код в терминале : Командаcloudshell edit app.pycloudshell editоткроет файлapp.pyв редакторе над терминалом. - Вставьте следующий код запуска приложения в
app.py:import streamlit as st from google import genai from google.genai import types import requests import logging # --- Defining variables and parameters --- REGION = "global" PROJECT_ID = None # TO DO: Insert Project ID GEMINI_MODEL_NAME = "gemini-2.5-flash" temperature = .2 top_p = 0.95 system_instructions = None # --- Tooling --- # TODO: Define the weather tool function declaration # TODO: Define the get_current_temperature function # --- Initialize the Vertex AI Client --- try: # TODO: Initialize the Vertex AI client print(f"VertexAI Client initialized successfully with model {GEMINI_MODEL_NAME}") except Exception as e: st.error(f"Error initializing VertexAI client: {e}") st.stop() # TODO: Add the get_chat function here in Task 15. # --- Call the Model --- def call_model(prompt: str, model_name: str) -> str: """ This function interacts with a large language model (LLM) to generate text based on a given prompt and system instructions. It will be replaced in a later step with a more advanced version that handles tooling. """ try: # TODO: Prepare the content for the model # TODO: Define generate_content configuration (needed for system instructions and parameters) # TODO: Define response logging.info(f"[call_model_response] LLM Response: \"{response.text}\"") # TODO: Uncomment the below "return response.text" line # return response.text except Exception as e: return f"Error: {e}" # --- Presentation Tier (Streamlit) --- # Set the title of the Streamlit application st.title("Travel Chat Bot") # Initialize session state variables if they don't exist if "messages" not in st.session_state: # Initialize the chat history with a welcome message st.session_state["messages"] = [ {"role": "assistant", "content": "How can I help you today?"} ] # Display the chat history for msg in st.session_state.messages: st.chat_message(msg["role"]).write(msg["content"]) # Get user input if prompt := st.chat_input(): # Add the user's message to the chat history st.session_state.messages.append({"role": "user", "content": prompt}) # Display the user's message st.chat_message("user").write(prompt) # Show a spinner while waiting for the model's response with st.spinner("Thinking..."): # Get the model's response using the call_model function model_response = call_model(prompt, GEMINI_MODEL_NAME) # Add the model's response to the chat history st.session_state.messages.append( {"role": "assistant", "content": model_response} ) # Display the model's response st.chat_message("assistant").write(model_response) - Создайте и откройте новый файл
requirements.txtдля кода приложения. Запустите следующий код в терминале : Командаcloudshell edit requirements.txtcloudshell editоткроет файлrequirements.txtв редакторе над терминалом. - Вставьте следующий стартовый код приложения в файл
requirements.txt.google-genai streamlit requests - Установите необходимые зависимости Python для этого проекта. Выполните следующий код в терминале :
uv pip install -r requirements.txt
7. Изучите код
Созданные вами файлы включают базовый интерфейс чат-приложения. Они включают:
-
app.py: Это файл, с которым мы будем работать. В настоящее время он содержит следующее:- необходимый импорт
- переменные среды и параметры (некоторые из которых являются заполнителями)
- пустая функция
call_model, которую мы будем заполнять - Streamlit-код для фронтенд-приложения чата
-
requirements.txt:- включает требования по установке для запуска
app.py
- включает требования по установке для запуска
Теперь пора изучить код!
Откройте чат Gemini Code Assist
Чат Gemini Code Assist должен быть открыт на панели справа в редакторе Cloud Shell. Если чат Gemini Code Assist ещё не открыт, вы можете открыть его, выполнив следующие действия:
- Нажав кнопку Gemini Code Assist (
) в верхней части экрана. - Выберите Открыть чат Gemini Code Assist .

Используйте Gemini Code Assist для понимания кода
Для лучшего понимания кода вы можете использовать чат Gemini Code Assist.
- Выделите или выберите нужный раздел кода.
- Введите «Объясните этот код» в чате Gemini.
- Нажмите Enter, чтобы отправить

8. Запустите веб-приложение.
Прежде чем подключать это приложение к LLM, запустите его, чтобы посмотреть, как оно будет себя вести на начальном этапе.
- Находясь в каталоге
wanderbot, выполните следующую команду в терминале , чтобы запустить приложение Streamlit и сделать его локально доступным в среде Cloud Shell: Оставьте это окно терминала открытым, так как приложение Streamlit продолжит работу. Вы можете открыть новое окно терминала в Cloud Shell для выполнения других команд.streamlit run app.py --browser.serverAddress=localhost --server.enableCORS=false --server.enableXsrfProtection=false --server.port 8080 - После выполнения команды нажмите кнопку Web Preview в верхней части редактора Cloud Shell и выберите Preview on port 8080 .

Вы увидите простой чат-интерфейс вашего туристического приложения. - Введите любое сообщение (например,
Hi!) и нажмите ENTER.
Вы заметите, что сообщение появится в истории чата, но вместо ответа от помощника вы получите сообщение об ошибке . Это связано с тем, что приложение ещё не подключено к большой языковой модели. Понаблюдайте за этим поведением, чтобы понять, с чего всё началось.
9. Инициализируйте клиент Vertex AI.
Изучите доступные модели в Vertex AI
Платформа Vertex AI от Google Cloud предоставляет доступ к различным моделям генеративного ИИ . Прежде чем интегрировать модель, вы можете изучить доступные варианты в консоли Google Cloud.
- В консоли Google Cloud перейдите в Model Garden. Для этого выполните поиск по запросу «Model Garden» в строке поиска в верхней части экрана и выберите Vertex AI.
) - Просмотрите доступные модели. Вы можете фильтровать их по таким параметрам, как модальность, типы задач и характеристики.
Для целей этой лабораторной работы вы будете использовать модель Gemini 2.5 Flash , которая является хорошим выбором для создания адаптивных чат-приложений благодаря своей скорости.
Инициализируйте клиент Vertex AI
Теперь вам нужно изменить раздел --- Initialize the Vertex AI Client --- в app.py чтобы инициализировать клиент Vertex AI. Этот клиентский объект будет использоваться для отправки подсказок модели.
- Откройте
app.pyв редакторе Cloud Shell. - В
app.pyнайдите строкуPROJECT_ID = None. - Замените
Noneна идентификатор вашего проекта Google Cloud в кавычках. (например,PROJECT_ID = "google-cloud-labs")
Если вы не можете вспомнить идентификатор своего проекта, вы можете перечислить все идентификаторы своих проектов с помощью:gcloud projects list | awk '/PROJECT_ID/{print $2}' - Определите клиента : внутри блока
tryинициализируйте клиента Vertex AI.client = genai.Client( vertexai=True, project=PROJECT_ID, location=REGION, )
Обновлена инициализация клиента Vertex AI.
На этом этапе раздел «Инициализация клиента Vertex AI» будет выглядеть следующим образом:
# --- Initialize the Vertex AI Client ---
try:
client = genai.Client(
vertexai=True,
project=PROJECT_ID,
location=REGION,
)
print(f"VertexAI Client initialized successfully with model {GEMINI_MODEL_NAME}")
except Exception as e:
st.error(f"Error initializing VertexAI client: {e}")
st.stop()
10. Подготовьте данные и вызовите модель.
Теперь вам нужно подготовить контент для отправки модели и совершить звонок модели Gemini.
- Найдите раздел
--- Call the Model ---, в котором определена функцияcall_model. - Определите содержимое : В разделе
# TODO: Prepare the content for the modelопределите входное содержимое, которое будет отправлено в модель. Для базового запроса это будет сообщение, которое вводит пользователь.contents = [prompt] - Определите ответ : вставьте этот код под
# TODO: Define response.response = client.models.generate_content( model=model_name, contents=contents, ) - Верните ответ : Раскомментируйте следующую строку:
return response.text - Проверьте строку вызова функции
call_modelв самом низу файла, в блокеwith. Если вы не понимаете, что здесь происходит, выделите строку и попросите Gemini Code Assist объяснить.
Более явный способ определения contents
Описанный выше способ определения contents работает, поскольку SDK достаточно интеллектуален, чтобы понимать, что список, содержащий строки, представляет собой текст, введенный пользователем. Он автоматически форматирует его для API модели.
Однако более явный и фундаментальный способ структурирования ввода предполагает использование объектов types.Part и types.Content , например:
user_message_parts = [types.Part.from_text(text=prompt)]
contents = [
types.Content(
role="user", # Indicates the content is from the user
parts=user_message_parts, # A list, allowing multiple types of content
),
]
Обновленная функция call_model
На этом этапе функция call_model должна выглядеть так:
def call_model(prompt: str, model_name: str) -> str:
"""
This function interacts with a large language model (LLM) to generate text based on a given prompt and system instructions.
It will be replaced in a later step with a more advanced version that handles tooling.
"""
try:
contents = [prompt]
# TODO: Define generate_content configuration (needed later for system instructions and parameters)
response = client.models.generate_content(
model=model_name,
contents=contents,
)
logging.info(f"[call_model_response] LLM Response: \"{response.text}\"")
return response.text
except Exception as e:
return f"Error: {e}"
11. Протестируйте подключенное приложение.
- В терминале завершите текущий запущенный процесс ( CTRL+C )
- Повторно выполните команду, чтобы снова запустить приложение Streamlit.
streamlit run app.py --browser.serverAddress=localhost --server.enableCORS=false --server.enableXsrfProtection=false --server.port 8080 - Обновите приложение Streamlit. Если приложение Streamlit всё ещё запущено, просто обновите страницу предварительного просмотра в браузере.
- Теперь введите вопрос в поле чата, например следующий:
What is the best time of year to go to Iceland? - Нажмите ENTER.
Вы должны увидеть, как приложение отобразит ваше сообщение, индикатор «Думаю...», а затем ответ, сгенерированный моделью Gemini! Если это так, то вы успешно подключили своё веб-приложение к LLM на Vertex AI. 🙌 🥳
12. Определите системные инструкции
Хотя базовая связь работает, качество и стиль ответов LLM во многом зависят от получаемых входных данных. Разработка подсказок — это процесс разработки и уточнения этих входных данных (подсказок), чтобы направить модель к получению желаемого результата.
Для этого вам нужно начать с создания некоторых системных инструкций и передачи их модели.
Вы будете использовать Ask Gemini , чтобы помочь себе придумать полезные системные инструкции.
- В
app.pyнайдите переменнуюsystem_instructions, которая в данный момент имеет значениеNone. Вам нужно заменитьsystem_instructions = NoneNoneна многострочную строку, содержащую инструкции для нашего бота-помощника по путешествиям. - Спросите Gemini Code Assist : Передайте следующую подсказку в Gemini Code Assist (или придумайте свою!):
I am a developer at a travel marketing company, and my sales department has decided that they need a new chat application to keep up with the bigger booking and search companies. I'm building a simple travel assistant chatbot using the Gemini 2.5 Flash model on Vertex AI. The application should: - Helps users ask questions about travel, book travel, and learn about places they are going to go - Provides users ways to get help about their specific travel plans - Provides all this in a production quality way (multiple environments, logging and monitoring, etc.) Please create system instructions appropriate for that chat app. Be thorough. Do not alter the code in any way beyond providing me with system instructions. - Определите
system_instructions: установитеsystem_instructionsравным системным инструкциям, сгенерированным с помощью Gemini Code Assist. Вы также можете использовать эти системные инструкции, созданные Gemini с аналогичным запросом.system_instructions = """ You are a sophisticated travel assistant chatbot designed to provide comprehensive support to users throughout their travel journey. Your capabilities include answering travel-related questions, assisting with booking travel arrangements, offering detailed information about destinations, and providing support for existing travel plans. **Core Functionalities:** 1. **Travel Information and Recommendations:** * Answer user inquiries about travel destinations, including popular attractions, local customs, visa requirements, weather conditions, and safety advice. * Provide personalized recommendations for destinations, activities, and accommodations based on user preferences, interests, and budget. * Offer insights into the best times to visit specific locations, considering factors like weather, crowds, and pricing. * Suggest alternative destinations or activities if the user's initial choices are unavailable or unsuitable. 2. **Booking Assistance:** * Facilitate the booking of flights, hotels, rental cars, tours, and activities. * Search for available options based on user-specified criteria such as dates, destinations, budget, and preferences. * Present clear and concise information about available options, including pricing, amenities, and booking terms. * Guide users through the booking process, ensuring accurate information and secure transactions. * Provide booking confirmations and relevant details, such as booking references and contact information. 3. **Travel Planning and Itinerary Management:** * Assist users in creating detailed travel itineraries, including flights, accommodations, activities, and transportation. * Offer suggestions for optimizing travel plans, such as minimizing travel time or maximizing sightseeing opportunities. * Provide tools for managing and modifying existing itineraries, including adding or removing activities, changing booking dates, or upgrading accommodations. * Offer reminders and notifications for upcoming travel events, such as flight check-in or tour departure times. 4. **Customer Support and Troubleshooting:** * Provide prompt and helpful support to users with questions or issues related to their travel plans. * Assist with resolving booking discrepancies, cancellations, or modifications. * Offer guidance on travel-related emergencies, such as lost luggage or travel delays. * Provide access to relevant contact information for airlines, hotels, and other travel providers. **Interaction Guidelines:** * **Professionalism:** Maintain a polite, respectful, and professional tone in all interactions. * **Clarity and Conciseness:** Provide clear, concise, and easy-to-understand information. Avoid jargon or technical terms unless necessary and always explain them. * **Accuracy:** Ensure all information provided is accurate and up-to-date. Double-check details before sharing them with users. If unsure about something, admit that you don't know and offer to find the information. * **Personalization:** Tailor your responses and recommendations to the specific needs and preferences of each user. * **Proactive Assistance:** Anticipate user needs and offer relevant information or suggestions proactively. * **Error Handling:** Gracefully handle user errors or misunderstandings. Provide helpful guidance and alternative options when necessary. * **Confidentiality:** Respect user privacy and handle personal information with the utmost confidentiality and in compliance with data protection regulations. **Example Interactions:** **User:** "I want to go on a beach vacation in the Caribbean. I have a budget of $2000 per person for a week." **Chatbot:** "Certainly! The Caribbean offers many beautiful beach destinations within your budget. Some popular options include Punta Cana in the Dominican Republic, Cancun in Mexico, and Montego Bay in Jamaica. These destinations offer stunning beaches, all-inclusive resorts, and various activities. Would you like me to search for flights and accommodations for these locations based on your travel dates?" **User:** "My flight is delayed. What should I do?" **Chatbot:** "I'm sorry to hear about the delay. Please check with the airline for the updated departure time and any assistance they can offer. You may be entitled to compensation or rebooking options depending on the length of the delay and the airline's policy. Do you have your flight number handy so I can look up the current status for you?" **User:** "Tell me about the best time to visit Japan." **Chatbot:** "Japan is a fantastic destination with distinct seasons offering unique experiences. Spring (March-May) is famous for the beautiful cherry blossoms, while autumn (September-November) boasts stunning fall foliage. Both seasons have pleasant temperatures, making them ideal for sightseeing. Summer (June-August) can be hot and humid, but it's a great time for festivals and outdoor activities in the mountains. Winter (December-February) offers opportunities for skiing and snowboarding in the Japanese Alps, though some areas may experience heavy snowfall. To recommend the best time for you, could you tell me what you'd like to experience in Japan?" By following these instructions, you will be able to provide exceptional travel assistance and create a positive experience for every user. """ - Определите конфигурацию generate_content: инициализируйте объект конфигурации, которому будут переданы эти системные инструкции. Поскольку
system_instructionsопределена в нашем скрипте глобально, функция может получить к нему прямой доступ.generate_content_config = types.GenerateContentConfig( system_instruction=[ types.Part.from_text(text=system_instructions) ], ) logging.info(f"[generate_config_details] System Instruction: {generate_content_config.system_instruction[0].text}") - Чтобы добавить системные инструкции в ответ , добавьте параметр
configв методgenerate contentи установите его равным объектуgenerate_content_config, созданному выше.response = client.models.generate_content( model=model_name, contents=contents, config=generate_content_config, # This is the new line )
Обновленная функция call_model
Полная функция call_model теперь выглядит так:
def call_model(prompt: str, model_name: str) -> str:
"""
This function interacts with a large language model (LLM) to generate text based on a given prompt and system instructions.
It will be replaced in a later step with a more advanced version that handles tooling.
"""
try:
contents = [prompt]
generate_content_config = types.GenerateContentConfig(
system_instruction=[
types.Part.from_text(text=system_instructions)
],
)
logging.info(f"[generate_config_details] System Instruction: {generate_content_config.system_instruction[0].text}")
response = client.models.generate_content(
model=model_name,
contents=contents,
config=generate_content_config,
)
logging.info(f"[call_model_response] LLM Response: \"{response.text}\"")
return response.text
except Exception as e:
return f"Error: {e}"
13. Протестируйте приложение с помощью системных инструкций.
- В терминале завершите текущий запущенный процесс ( CTRL+C )
- Повторно выполните команду, чтобы снова запустить приложение Streamlit.
streamlit run app.py --browser.serverAddress=localhost --server.enableCORS=false --server.enableXsrfProtection=false --server.port 8080 - Обновите приложение Streamlit. Если приложение Streamlit всё ещё запущено, просто обновите страницу предварительного просмотра в браузере.
- Попробуйте задать тот же вопрос, что и раньше:
What is the best time of year to go to Iceland? - Нажмите ENTER.
Сравните реакцию на этот раз с реакцией в прошлый раз.
14. Дайте определение погодному инструменту
Пока что наш чат-бот обладает знаниями, но их объём ограничен данными, на которых он был обучен. Он не имеет доступа к информации в режиме реального времени. Для бота, специализирующегося на путешествиях, возможность получать актуальные данные, например, прогнозы погоды, — огромное преимущество.
Вот тут-то и вступает в дело инструментарий , также известный как вызов функций . Мы можем определить набор инструментов (функций Python), которые LLM может вызвать для получения внешней информации.
Как работает инструмент
- Мы описываем наши инструменты для модели, включая то, что они делают и какие параметры они принимают.
- Пользователь отправляет подсказку (например, « Какая погода в Лондоне? »).
- Модель получает подсказку и видит, что пользователь спрашивает о чем-то, что она может выяснить с помощью одного из своих инструментов.
- Вместо ответа текстом модель отвечает специальным объектом
function_call, указывающим, какой инструмент она хочет вызвать и с какими аргументами. - Наш код Python получает этот
function_call, выполняет нашу фактическую функциюget_current_temperatureс предоставленными аргументами и получает результат (например, 15°C). - Мы отправляем этот результат обратно в модель.
- Модель получает результат и генерирует ответ на естественном языке для пользователя (например, «Текущая температура в Лондоне составляет 15°C»).
Этот процесс позволяет модели отвечать на вопросы, выходящие за рамки ее тренировочных данных, что делает ее гораздо более мощным и полезным помощником.
Определить инструмент погоды
Если путешественник ищет совет, чем заняться, и выбирает между различными видами деятельности, зависящими от погоды, инструмент для прогнозирования погоды может оказаться полезным! Давайте создадим инструмент для нашей модели, который будет получать текущую погоду. Нам понадобятся две части: объявление функции, описывающее инструмент для модели, и сама функция Python, реализующая его.
- В
app.pyнайдите комментарий# TODO: Define the weather tool function declaration. - Под этим комментарием добавьте переменную
weather_function. Это словарь, который сообщает модели всю необходимую информацию о назначении функции, её параметрах и необходимых аргументах.weather_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"], }, } - Затем найдите комментарий
# TODO: Define the get_current_temperature function. Под ним добавьте следующий код Python. Эта функция:- Вызовите API геокодирования, чтобы получить координаты местоположения.
- Используйте эти координаты для вызова API погоды .
- Возвращает простую строку с температурой и единицей измерения.
def get_current_temperature(location: str) -> str: """Gets the current temperature for a given location.""" try: # --- Get Latitude and Longitude for the location --- geocode_url = f"https://geocoding-api.open-meteo.com/v1/search?name={location}&count=1&language=en&format=json" geocode_response = requests.get(geocode_url) geocode_data = geocode_response.json() if not geocode_data.get("results"): return f"Could not find coordinates for {location}." lat = geocode_data["results"][0]["latitude"] lon = geocode_data["results"][0]["longitude"] # --- Get Weather for the coordinates --- weather_url = f"https://api.open-meteo.com/v1/forecast?latitude={lat}&longitude={lon}¤t_weather=true" weather_response = requests.get(weather_url) weather_data = weather_response.json() temperature = weather_data["current_weather"]["temperature"] unit = "°C" return f"{temperature}{unit}" except Exception as e: return f"Error fetching weather: {e}"
15. Рефакторинг для чата и инструментов
Наша текущая функция call_model использует простой однократный вызов generate_content . Это отлично подходит для отдельных вопросов, но не идеально для многовариантного диалога, особенно если он предполагает обмен инструментами.
Более эффективным решением будет использование сеанса чата , сохраняющего контекст беседы. Теперь мы реорганизуем наш код для использования сеанса чата, необходимого для корректной реализации инструментария.
- Удалите существующую функцию
call_model. Мы заменим её более продвинутой версией. - Вместо неё добавьте новую функцию
call_modelиз блока кода ниже. Эта новая функция содержит логику для обработки цикла вызова инструментов, который мы обсуждали ранее. Обратите внимание, что в ней есть несколько комментариев TODO, которые мы заполним на следующих шагах.# --- Call the Model --- def call_model(prompt: str, model_name: str) -> str: """ This function interacts with a large language model (LLM) to generate text based on a given prompt. It maintains a chat session and handles function calls from the model to external tools. """ try: # TODO: Get the existing chat session or create a new one. message_content = prompt # Start the tool-calling loop while True: # TODO: Send the message to the model. # Check if the model wants to call a tool has_tool_calls = False for part in response.candidates[0].content.parts: if part.function_call: has_tool_calls = True function_call = part.function_call logging.info(f"Function to call: {function_call.name}") logging.info(f"Arguments: {function_call.args}") # TODO: Call the appropriate function if the model requests it. # If no tool call was made, break the loop if not has_tool_calls: break # TODO: Return the model's final text response. except Exception as e: return f"Error: {e}" - Теперь добавим вспомогательную функцию для управления сеансом чата. Над новой функцией
call_modelдобавьте функциюget_chat. Эта функция создаст новый сеанс чата с системными инструкциями и определениями инструментов или извлечет существующий. Это хорошая практика для организации кода.def get_chat(model_name: str): if f"chat-{model_name}" not in st.session_state: # TODO: Define the tools configuration for the model # TODO: Define the generate_content configuration, including tools # TODO: Create a new chat session st.session_state[f"chat-{model_name}"] = chat return st.session_state[f"chat-{model_name}"]
Теперь вы заложили основу для нашей продвинутой логики чата с поддержкой инструментов!
16. Реализуйте логику вызова инструментов.
Теперь давайте заполним TODOs , чтобы сделать нашу логику вызова инструментов полностью функциональной.
Реализовать get_chat
- В функции
get_chatв комментарии# TODO: Define the tools configuration...определите объектtools, создав экземплярtypes.Toolиз нашего объявленияweather_function.tools = types.Tool(function_declarations=[weather_function]) - В разделе
# TODO: Define the generate_content configuration...определитеgenerate_content_config, обязательно передав объектtoolsмодели. Так модель узнает об инструментах, которые она может использовать.generate_content_config = types.GenerateContentConfig( system_instruction=[types.Part.from_text(text=system_instructions)], tools=[tools] # Pass the tool definition here ) - В разделе
# TODO: Create a new chat sessionсоздайте объект чата с помощьюclient.chats.create(), передав имя нашей модели и конфигурацию.chat = client.chats.create( model=model_name, config=generate_content_config, )
Реализовать call_model
- В разделе
# TODO: Get the existing chat session...в функцииcall_modelвызовите нашу новую вспомогательную функциюget_chat.chat = get_chat(model_name) - Далее найдите
# TODO: Send the message to the model. Отправьте сообщение пользователю, используя методchat.send_message().response = chat.send_message(message_content) - Найти
# TODO: Call the appropriate function.... Здесь мы проверяем, какую функцию хочет модель, и выполняем ее.
if function_call.name == "get_current_temperature":
result = get_current_temperature(**function_call.args)
function_response_part = types.Part.from_function_response(
name=function_call.name,
response={"result": result},
)
message_content = [function_response_part]
- Наконец, найдите
# TODO: Return the model's final text responseи добавьте оператор возврата.return response.text
Обновленная функция get_chat
Обновленная функция get_chat теперь должна выглядеть так:
def get_chat(model_name: str):
if f"chat-{model_name}" not in st.session_state:
#Tools
tools = types.Tool(function_declarations=[weather_function])
# Initialize a confiburation object
generate_content_config = types.GenerateContentConfig(
system_instruction=[types.Part.from_text(text=system_instructions)],
tools=[tools]
)
chat = client.chats.create(
model=model_name,
config=generate_content_config,
)
st.session_state[f"chat-{model_name}"] = chat
return st.session_state[f"chat-{model_name}"]
Обновленная функция call_model
Обновленная функция call_model теперь должна выглядеть так:
def call_model(prompt: str, model_name: str) -> str:
try:
chat = get_chat(model_name)
message_content = prompt
while True:
response = chat.send_message(message_content)
has_tool_calls = False
for part in response.candidates[0].content.parts:
if part.function_call:
has_tool_calls = True
function_call = part.function_call
logging.info(f"Function to call: {function_call.name}")
logging.info(f"Arguments: {function_call.args}")
if function_call.name == "get_current_temperature":
result = get_current_temperature(**function_call.args)
function_response_part = types.Part.from_function_response(
name=function_call.name,
response={"result": result},
)
message_content = [function_response_part]
elif part.text:
logging.info("No function call found in the response.")
logging.info(response.text)
if not has_tool_calls:
break
return response.text
except Exception as e:
return f"Error: {e}"
17. Протестируйте приложение с поддержкой инструмента
Давайте посмотрим на вашу новую функцию в действии!
- В терминале завершите текущий запущенный процесс ( CTRL+C )
- Повторно выполните команду, чтобы снова запустить приложение Streamlit.
streamlit run app.py --browser.serverAddress=localhost --server.enableCORS=false --server.enableXsrfProtection=false --server.port 8080 - Обновите приложение Streamlit. Если приложение Streamlit всё ещё запущено, просто обновите страницу предварительного просмотра в браузере.
- Теперь задайте вопрос, который должен активировать ваш новый инструмент, например, следующий:
I'm looking for something to do in New York today. What do you recommend? Would it be a good day to go to Ellis Island? - Нажмите ENTER
Сравните этот ответ с предыдущими. В чём разница?
Вы должны увидеть ответ, включающий температуру из вашей функции! Проверьте также терминал Cloud Shell: вы должны увидеть операторы печати, подтверждающие выполнение вашей функции Python.
18. Уточните выходные данные модели с помощью параметров
Отличная работа! Теперь ваш помощник в путешествиях может использовать инструменты для получения внешних данных в режиме реального времени, что делает его значительно более эффективным.
Теперь, когда мы улучшили возможности нашей модели, давайте настроим её реакцию. Параметры модели позволяют управлять стилем и степенью случайности текста, генерируемого LLM. Изменяя эти настройки, вы можете сделать вывод бота более целенаправленным и детерминированным или более креативным и разнообразным.
В этой лабораторной работе мы сосредоточимся на temperature и top_p . (Полный список настраиваемых параметров и их описания см. в GenerateContentConfig в нашем справочнике по API.)
-
temperature: управляет случайностью вывода. Более низкое значение (ближе к 0) делает вывод более детерминированным и целенаправленным, а более высокое значение (ближе к 2) увеличивает случайность и креативность. Для бота вопросов и ответов или помощника более низкая температура обычно предпочтительна для более последовательных и содержательных ответов. -
top_p: максимальная кумулятивная вероятность токенов, учитываемых при выборке. Токены сортируются на основе присвоенных им вероятностей, так что учитываются только наиболее вероятные токены. Модель учитывает наиболее вероятные токены, сумма вероятностей которых равна значениюtop_p. Более низкое значение ограничивает выбор токенов, что приводит к менее разнообразному результату.
Параметры вызова
- Найдите переменные
temperatureиtop_p, определённые в начале файлаapp.pyОбратите внимание, что они ещё нигде не вызывались. - Добавьте
temperatureиtop_pк параметрам, определенным вGenerateContentConfigв функцииcall_model.generate_content_config = types.GenerateContentConfig( temperature=temperature, top_p=top_p, system_instruction=[types.Part.from_text(text=system_instructions)], tools=[tools] # Pass the tool definition here )
Обновленная функция get_chat
Приложение get_chat теперь выглядит так:
def get_chat(model_name: str):
if f"chat-{model_name}" not in st.session_state:
#Tools
tools = types.Tool(function_declarations=[weather_function])
# Initialize a confiburation object
generate_content_config = types.GenerateContentConfig(
temperature=temperature,
top_p=top_p,
system_instruction=[types.Part.from_text(text=system_instructions)],
tools=[tools]
)
chat = client.chats.create(
model=model_name,
config=generate_content_config,
)
st.session_state[f"chat-{model_name}"] = chat
return st.session_state[f"chat-{model_name}"]
19. Тест с параметрами модели
- В терминале завершите текущий запущенный процесс ( CTRL+C )
- Повторно выполните команду, чтобы снова запустить приложение Streamlit.
streamlit run app.py --browser.serverAddress=localhost --server.enableCORS=false --server.enableXsrfProtection=false --server.port 8080 - Обновите приложение Streamlit. Если приложение Streamlit всё ещё запущено, просто обновите страницу предварительного просмотра в браузере.
- Попробуйте задать тот же вопрос, что и раньше,
I'm looking for something to do in New York today. What do you recommend? Would it be a good day to go to Ellis Island? - Нажмите ENTER
Сравните этот ответ с более ранними ответами.
20. Поздравляем!
Вы успешно обновили свое приложение «Вопросы и ответы» с помощью инструментария — мощной функции, которая позволяет вашему приложению на базе Gemini взаимодействовать с внешними системами и получать доступ к информации в режиме реального времени.
Продолжение экспериментов
Существует множество вариантов дальнейшей оптимизации вашего запроса. Вот некоторые из них, которые стоит рассмотреть:
- Отрегулируйте
temperatureиtop_pи посмотрите, как это изменит реакцию LLM. - Полный список настраиваемых параметров и их описание см. в разделе
GenerateContentConfigв нашем справочнике по API. Попробуйте определить больше параметров и изменить их, чтобы посмотреть, что из этого получится!
Резюме
В этой лабораторной работе вы выполнили следующее:
- Для разработки использовался Cloud Shell Editor и терминал.
- Используйте Vertex AI Python SDK для подключения вашего приложения к модели Gemini.
- Применял системные инструкции и параметры модели для руководства ответами LLM.
- Изучил концепцию инструментирования ( вызова функций ) и ее преимущества.
- Измените код, чтобы использовать сеанс чата с сохранением состояния — наилучшую практику для разговорного ИИ.
- Определил инструмент для модели с помощью объявления функции.
- Реализовал функцию Python для реализации логики инструмента.
- Написал код для обработки запросов на вызов функций модели и возврата результатов.