-
Notifications
You must be signed in to change notification settings - Fork 410
update to add hello world sample #311
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
update to add hello world sample #311
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Summary of Changes
Hello @butlfrazp, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!
I've added a new "Hello World" sample for an Azure AI Foundry agent. This sample demonstrates the fundamental capabilities of an Azure AI agent, complete with a modern web interface for real-time chat, a command-line interface for various operations, and comprehensive documentation. It's designed to be a straightforward starting point for anyone looking to understand or build agents using Azure AI Foundry, offering both a fully functional Azure-connected mode and a convenient demo mode that doesn't require Azure credentials.
Highlights
- New Sample Application: This pull request introduces a brand new "Hello World" sample for an Azure AI Foundry agent, providing a minimal yet complete example of how to build and interact with such an agent.
- Interactive Web Interface: A modern web interface is included, built with Starlette, featuring real-time chat via WebSockets, responsive design for various devices, and visual feedback like typing indicators.
- Enhanced Documentation: Comprehensive documentation has been added, including a detailed
DEVELOPMENT.md
for setup, testing, and deployment, and an updatedREADME.md
for quick understanding and usage. - CLI Tools for Management: The sample now includes a command-line interface (
cli.py
) for easy management, allowing users to run the web server, interact via a console demo, and check environment configurations. - Practical Usage Examples: A dedicated
examples/
directory provides various usage scenarios, such assimple_chat.py
for basic interaction,multi_turn.py
for conversational flow, anderror_handling.py
to demonstrate robust error management. - Docker Integration: The sample is fully containerized with a
Dockerfile
anddocker-compose.yml
, enabling seamless development and deployment in Docker environments. - Demo Mode with Mock Agent: A
mock_agent.py
has been implemented, allowing the web UI to run in a demo mode without requiring actual Azure AI Foundry credentials, making it easier for new users to get started.
Using Gemini Code Assist
The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.
Invoking Gemini
You can request assistance from Gemini at any point in your pull request via creating an issue comment (i.e. comment on the pull request page) using either /gemini <command>
or @gemini-code-assist <command>
. Below is a summary of the supported commands.
Feature | Command | Description |
---|---|---|
Code Review | /gemini review |
Performs a code review for the current pull request in its current state. |
Pull Request Summary | /gemini summary |
Provides a summary of the current pull request in its current state. |
Comment | @gemini-code-assist | Responds in comments when explicitly tagged, both in issue comments and review comments. |
Help | /gemini help |
Displays a list of available commands. |
Customization
To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/
folder in the base of the repository. Detailed instructions can be found here.
Limitations & Feedback
Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments or fill out our survey to provide feedback.
You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.
Footnotes
-
Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution. ↩
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Code Review
This pull request introduces a comprehensive "Hello World" sample for the Azure AI Foundry Agent, complete with a Starlette web application, a real-time chat UI, a command-line interface, example scripts, Docker support, and tests. The project is well-structured and provides a solid foundation for users. My review focuses on enhancing correctness, maintainability, and addressing several inconsistencies in the documentation and configuration. The key recommendations include fixing the Docker health check which currently fails, replacing a blocking call in asynchronous code to prevent performance issues, and resolving module pathing problems to improve the project's robustness and ease of use.
WORKDIR /app | ||
|
||
# Install system dependencies | ||
RUN apt-get update && apt-get install -y \ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The HEALTHCHECK
instruction relies on curl
to check the application's health. However, the curl
command is not available in the python:3.11-slim
base image and is not installed in the preceding RUN
command. This will cause the health check to fail, potentially leading Docker or container orchestrators to incorrectly terminate the container.
RUN apt-get update && apt-get install -y \
build-essential \
curl
and iterations < max_iterations | ||
): | ||
iterations += 1 | ||
time.sleep(1) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using time.sleep()
in an async
function is a blocking operation that will halt the entire asyncio event loop. This can severely degrade the performance and responsiveness of the application, as no other concurrent tasks can execute during the sleep period. The non-blocking await asyncio.sleep()
should be used instead.
time.sleep(1) | |
await asyncio.sleep(1) |
|
||
```bash | ||
# Development with auto-reload | ||
docker-compose -f docker-compose.dev.yml up |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- `streaming_response.py` - Streaming responses (if supported) | ||
- `context_management.py` - Managing conversation context | ||
- `custom_instructions.py` - Using custom instructions |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The documentation for examples lists several advanced example files (streaming_response.py
, context_management.py
, custom_instructions.py
) that are not present in the project. This could be confusing for users who are looking for these specific implementations.
- `streaming_response.py` - Streaming responses (if supported) | |
- `context_management.py` - Managing conversation context | |
- `custom_instructions.py` - Using custom instructions | |
- `simple_chat.py` - Simple one-off conversation | |
- `multi_turn.py` - Multi-turn conversation example | |
- `error_handling.py` - Error handling demonstration |
|
||
try: | ||
# Run the Starlette server | ||
run_server(host="0.0.0.0", port=8000, reload=True) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The main entry point for the package hardcodes reload=True
when running the server. While this is convenient for development, it's not ideal for a default execution mode, as reloading is less stable and consumes more resources. It's better to default to reload=False
and allow development tools or the CLI to enable it explicitly.
run_server(host="0.0.0.0", port=8000, reload=True) | |
run_server(host="0.0.0.0", port=8000, reload=False) |
from pathlib import Path | ||
|
||
# Add the current directory to the Python path | ||
sys.path.insert(0, str(Path(__file__).parent)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This script modifies sys.path
to handle imports, which is an anti-pattern that can make the import system fragile and dependent on the execution context. For a more robust solution, this script should be run as a module from the project root (e.g., python -m hello_world_agent.client
), and the sys.path
manipulation should be removed.
DEMO_MODE = os.getenv("DEMO_MODE", "false").lower() == "true" | ||
|
||
# Global storage for agents and sessions | ||
active_agents: Dict[str, HelloWorldAgent] = {} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The type hint for active_agents
is Dict[str, HelloWorldAgent]
, but in demo mode, instances of MockAgent
are stored in this dictionary. This creates a type inconsistency. Using typing.Any
or a Union
type would make the type hint accurate and prevent potential issues with static analysis tools.
active_agents: Dict[str, HelloWorldAgent] = {} | |
active_agents: Dict[str, Any] = {} |
<script src="https://unpkg.com/[email protected]"></script> | ||
<script src="https://unpkg.com/htmx.org/dist/ext/ws.js"></script> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This HTML file includes the htmx
library and its WebSocket extension. However, the custom JavaScript in the <script>
tag at the bottom of the file implements all the chat logic using the native WebSocket
API and does not use htmx
at all. These included scripts are unused dependencies and should be removed to reduce page load time and complexity.
from pathlib import Path | ||
|
||
# Add the parent directory to the Python path for imports | ||
sys.path.insert(0, str(Path(__file__).parent.parent)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
assert "Hello World agent" in instructions | ||
assert "friendly" in instructions.lower() | ||
|
||
@patch('hello_agent.AgentsClient') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The targets for patch
are specified as relative paths (e.g., 'hello_agent.AgentsClient'
). This is fragile and depends on sys.path
being configured in a specific way. It's best practice to use the fully qualified path of the object where it is being looked up. In this case, it should be 'hello_world_agent.hello_agent.AgentsClient'
. This applies to the other patches in this test class as well.
@patch('hello_world_agent.hello_agent.AgentsClient')
Description
Thank you for opening a Pull Request!
Before submitting your PR, there are a few things you can do to make sure it goes smoothly:
CONTRIBUTING
Guide.Fixes #<issue_number_goes_here> 🦕