Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 35 additions & 0 deletions .github/copilot-instructions.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
# GitHub Copilot Instructions

## Repository Layout Rules

### Root-level files
The root of this repository must contain **only**:
- `README.md` — the main repository readme
- `LICENSE` — the license file

All other documentation, planning documents, and policy files must be placed in the `docs/` folder at the root of the repository.

### docs/ folder
The `docs/` folder at the root of the repository is the single location for:
- Planning documents (e.g., modernization plans, roadmaps)
- Policy files (e.g., CODE_OF_CONDUCT.md, SECURITY.md, SUPPORT.md)
- Any other repository-wide documentation that is not a `README.md` or `LICENSE`

**This rule does NOT apply to documentation that belongs to individual samples.**
Each sample folder (e.g., `02.CreateYourFirstAgent/`, `07.Workflow/`, `09.Cases/`) may contain its own `README.md` and any documentation files specific to that sample.

### Sample folders
Each numbered chapter folder and its sub-folders may freely contain:
- `README.md`
- Sample-specific documentation and assets (images, diagrams, etc.)
- Code files and project files

### Summary

| Location | Allowed files |
|---|---|
| Repo root | `README.md`, `LICENSE` only |
| `docs/` | All repo-wide docs, plans, and policy files |
| Any sample/chapter folder | `README.md`, sample-specific docs, code |

When creating new planning documents, policy files, or repository-wide documentation, always place them in `docs/` — never at the repo root.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@
*.userosscache
*.sln.docstates
*.env
# Note: .NET user-secrets (dotnet user-secrets set ...) are stored outside the
# repository in your OS user profile and are never committed to git.

# User-specific files (MonoDevelop/Xamarin Studio)
*.userprefs
Expand Down

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
using System;
using System;
using System.ComponentModel;
using System.ClientModel;
using Microsoft.Extensions.AI;
using Microsoft.Agents.AI;
using OpenAI;
using DotNetEnv;
using Microsoft.Extensions.Configuration;

// Load environment variables from .env file
Env.Load("../../../../.env");

// Tool: Random Destination Generator
[Description("Provides a random vacation destination.")]
Expand All @@ -31,11 +30,15 @@ static string GetRandomDestination()
return destinations[index];
}

// Get GitHub Models configuration from environment variables
var github_endpoint = Environment.GetEnvironmentVariable("GITHUB_ENDPOINT")
var config = new ConfigurationBuilder()
.AddUserSecrets<Program>()
.AddEnvironmentVariables()
.Build();

var github_endpoint = config["GITHUB_ENDPOINT"]
?? throw new InvalidOperationException("GITHUB_ENDPOINT is not set.");
var github_model_id = Environment.GetEnvironmentVariable("GITHUB_MODEL_ID") ?? "gpt-4o-mini";
var github_token = Environment.GetEnvironmentVariable("GITHUB_TOKEN")
var github_model_id = config["GITHUB_MODEL_ID"] ?? "gpt-4o-mini";
var github_token = config["GITHUB_TOKEN"]
?? throw new InvalidOperationException("GITHUB_TOKEN is not set.");

// Configure OpenAI client for GitHub Models
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# Tool Use (.NET)

Shows how to build a stateful agent conversation using `AgentSession`. A travel-planning agent uses a custom tool to suggest destinations across multiple sequential turns, demonstrating how session context is preserved between calls.

## What it shows
- Creating and managing an `AgentSession` for multi-turn conversations
- Registering and invoking a C# function as an agent tool
- How the agent autonomously decides when to call a tool based on user input

## Prerequisites
- [.NET 10 SDK](https://dot.net)
- A [GitHub Models](https://github.com/marketplace/models) personal access token

## Configure secrets

```bash
dotnet user-secrets set "GITHUB_TOKEN" "<your-github-pat>"
dotnet user-secrets set "GITHUB_ENDPOINT" "https://models.inference.ai.azure.com"
dotnet user-secrets set "GITHUB_MODEL_ID" "gpt-4o-mini"
```

## Run

```bash
dotnet run
```

## Run with file-based approach (.NET 10)

```bash
dotnet run app.cs
```
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
// File-based run: dotnet run app.cs
#:property UserSecretsId c2c7f177-4a84-4250-9357-98122c3f2feb
#:package Microsoft.Extensions.AI@10.3.0
#:package Microsoft.Extensions.AI.OpenAI@10.3.0
#:package OpenAI@2.8.0
#:package Microsoft.Agents.AI@1.0.0-rc1
#:package Microsoft.Agents.AI.OpenAI@1.0.0-rc1
#:package Microsoft.Extensions.Configuration.UserSecrets@10.0.0
#:package Microsoft.Extensions.Configuration.EnvironmentVariables@10.0.0

using System;
using System.ComponentModel;
using System.ClientModel;
using Microsoft.Extensions.AI;
using Microsoft.Agents.AI;
using OpenAI;
using Microsoft.Extensions.Configuration;

// Load environment variables from .env file

// Tool: Random Destination Generator
[Description("Provides a random vacation destination.")]
static string GetRandomDestination()
{
var destinations = new List<string>
{
"Paris, France",
"Tokyo, Japan",
"New York City, USA",
"Sydney, Australia",
"Rome, Italy",
"Barcelona, Spain",
"Cape Town, South Africa",
"Rio de Janeiro, Brazil",
"Bangkok, Thailand",
"Vancouver, Canada"
};
var random = new Random();
int index = random.Next(destinations.Count);
return destinations[index];
}

var config = new ConfigurationBuilder()
.AddUserSecrets<Program>()
.AddEnvironmentVariables()
.Build();

var github_endpoint = config["GITHUB_ENDPOINT"]
?? throw new InvalidOperationException("GITHUB_ENDPOINT is not set.");
var github_model_id = config["GITHUB_MODEL_ID"] ?? "gpt-4o-mini";
var github_token = config["GITHUB_TOKEN"]
?? throw new InvalidOperationException("GITHUB_TOKEN is not set.");

// Configure OpenAI client for GitHub Models
var openAIOptions = new OpenAIClientOptions()
{
Endpoint = new Uri(github_endpoint)
};
var openAIClient = new OpenAIClient(new ApiKeyCredential(github_token), openAIOptions);

// Create AI Agent with tool integration
AIAgent agent = openAIClient.GetChatClient(github_model_id).AsIChatClient().AsAIAgent(
instructions: "You are a helpful AI Agent that can help plan vacations for customers at random destinations.",
tools: [AIFunctionFactory.Create((Func<string>)GetRandomDestination)]
);

// Create conversation thread for context
AgentSession session = await agent.CreateSessionAsync();

// Run agent with tool invocation
Console.WriteLine(await agent.RunAsync("Plan me a day trip", session));

// Follow-up request to demonstrate tool re-invocation
Console.WriteLine(await agent.RunAsync("I don't like that destination. Plan me another vacation.", session));
Original file line number Diff line number Diff line change
@@ -1,24 +1,30 @@
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net10.0</TargetFramework>
<RootNamespace>dotnet_agent_framework_ghmodels_tool</RootNamespace>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<UserSecretsId>c2c7f177-4a84-4250-9357-98122c3f2feb</UserSecretsId>
</PropertyGroup>


<ItemGroup>
<PackageReference Include="DotNetEnv" Version="3.1.1" />
<PackageReference Include="Microsoft.Extensions.AI" Version="10.2.0" />
<PackageReference Include="Microsoft.Extensions.AI.OpenAI" Version="10.2.0-preview.1.26063.2" />
<PackageReference Include="Microsoft.Extensions.AI" Version="10.3.0" />
<PackageReference Include="Microsoft.Extensions.AI.OpenAI" Version="10.3.0" />
<PackageReference Include="OpenAI" Version="2.8.0" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="/Users/lokinfey/Desktop/AOAI/Foundry/agent-framework/dotnet/src/Microsoft.Agents.AI.OpenAI/Microsoft.Agents.AI.OpenAI.csproj" />
<ProjectReference Include="/Users/lokinfey/Desktop/AOAI/Foundry/agent-framework/dotnet/src/Microsoft.Agents.AI/Microsoft.Agents.AI.csproj" />
<PackageReference Include="Microsoft.Agents.AI" Version="1.0.0-rc1" />
<PackageReference Include="Microsoft.Agents.AI.OpenAI" Version="1.0.0-rc1" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.Extensions.Configuration.UserSecrets" Version="10.0.0" />
<PackageReference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" Version="10.0.0" />
</ItemGroup>


</Project>
<ItemGroup>
<Compile Remove="app.cs" />
</ItemGroup>
</Project>
Original file line number Diff line number Diff line change
@@ -1,18 +1,20 @@
using System.ClientModel;
using System.ClientModel;
using Azure.AI.Projects;
using Azure.Identity;
using Microsoft.Agents.AI;
using Microsoft.Extensions.AI;
using OpenAI;
using OpenAI.Files;
using OpenAI.VectorStores;
using DotNetEnv;
using Microsoft.Extensions.Configuration;

var config = new ConfigurationBuilder()
.AddUserSecrets<Program>()
.AddEnvironmentVariables()
.Build();

Env.Load("/Users/lokinfey/Desktop/AOAI/Foundry/Agent-Framework-Samples/.env");

var endpoint = Environment.GetEnvironmentVariable("AZURE_AI_PROJECT_ENDPOINT") ?? throw new InvalidOperationException("AZURE_AI_PROJECT_ENDPOINT is not set.");
var deploymentName = Environment.GetEnvironmentVariable("AZURE_AI_MODEL_DEPLOYMENT_NAME") ?? "gpt-4o-mini";
var endpoint = config["AZURE_AI_PROJECT_ENDPOINT"] ?? throw new InvalidOperationException("AZURE_AI_PROJECT_ENDPOINT is not set.");
var deploymentName = config["AZURE_AI_MODEL_DEPLOYMENT_NAME"] ?? "gpt-4o-mini";

// Create an AI Project client and get an OpenAI client that works with the foundry service.
AIProjectClient aiProjectClient = new(
Expand Down
Loading