Skip to content

Commit 09fbccf

Browse files
SergeyMenshykhsemenshiCopilot
authored
.NET: Add AgentSkillsSourceContext to AgentSkillsSource.GetSkillsAsync (microsoft#6797)
* Add AgentSkillsSourceContext to AgentSkillsSource.GetSkillsAsync Pass agent/session context through the skills retrieval pipeline so sources, filters, and caching can make context-aware decisions. - AgentSkillsSourceContext (Agent, Session) is built by AgentSkillsProvider from the InvokingContext and flows through all sources and decorators. - FilteringAgentSkillsSource predicate now receives an AgentSkillFilterContext bundling the skill and the source context. - CachingAgentSkillsSource supports per-key isolation via CachingAgentSkillsSourceOptions.CacheIsolationKeySelector; a null selector preserves the shared-cache behavior. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * Make AgentSkillsSourceContext constructor public and harden cache key - Make the AgentSkillsSourceContext constructor public so external callers can invoke AgentSkillsSource.GetSkillsAsync directly; drop the Mcp.UnitTests InternalsVisibleTo entry it required. - Use a dedicated sentinel cache key for the shared bucket so an isolation selector returning an empty string gets its own bucket. - Document cache-key cardinality guidance and baseline the experimental API breaking changes in CompatibilitySuppressions.xml. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * Drop AgentSkillFilterContext in favor of a two-argument filter predicate Replace the AgentSkillFilterContext bundle with a Func<AgentSkill, AgentSkillsSourceContext, bool> predicate in FilteringAgentSkillsSource and AgentSkillsProviderBuilder.UseFilter, and update the tests accordingly. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --------- Co-authored-by: SergeyMenshykh <SergeMenshikh@outlook.com> Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
1 parent 4cb1a66 commit 09fbccf

31 files changed

Lines changed: 620 additions & 158 deletions

dotnet/src/Microsoft.Agents.AI.Mcp/Skills/AgentMcpSkillsSource.cs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ public AgentMcpSkillsSource(McpClient client, AgentMcpSkillsSourceOptions? optio
7878
}
7979

8080
/// <inheritdoc/>
81-
public override async Task<IList<AgentSkill>> GetSkillsAsync(CancellationToken cancellationToken = default)
81+
public override async Task<IList<AgentSkill>> GetSkillsAsync(AgentSkillsSourceContext context, CancellationToken cancellationToken = default)
8282
{
8383
if (this.TryGetCachedSkills() is { } cached)
8484
{
@@ -99,7 +99,7 @@ public override async Task<IList<AgentSkill>> GetSkillsAsync(CancellationToken c
9999
{
100100
// The refresh owner uses CancellationToken.None so that a single caller's cancellation
101101
// does not abort the shared refresh for all concurrent waiters.
102-
var skills = await this.GetCoreSkillsAsync(CancellationToken.None).ConfigureAwait(false);
102+
var skills = await this.GetCoreSkillsAsync(context, CancellationToken.None).ConfigureAwait(false);
103103

104104
this.UpdateCache(skills);
105105

@@ -155,7 +155,7 @@ private void UpdateCache(IList<AgentSkill> skills)
155155
/// Reads the skill index from the MCP server, dispatches entries to registered loaders, and
156156
/// returns the aggregated skill list.
157157
/// </summary>
158-
private async Task<IList<AgentSkill>> GetCoreSkillsAsync(CancellationToken cancellationToken)
158+
private async Task<IList<AgentSkill>> GetCoreSkillsAsync(AgentSkillsSourceContext context, CancellationToken cancellationToken)
159159
{
160160
McpSkillIndex? index = await this.TryReadIndexAsync(cancellationToken).ConfigureAwait(false);
161161

@@ -185,7 +185,7 @@ private async Task<IList<AgentSkill>> GetCoreSkillsAsync(CancellationToken cance
185185
foreach (var loader in this._loaders.Values)
186186
{
187187
var entries = entriesByType.TryGetValue(loader.EntryType, out List<McpSkillIndexEntry>? matched) ? matched : [];
188-
skills.AddRange(await loader.LoadAsync(entries, cancellationToken).ConfigureAwait(false));
188+
skills.AddRange(await loader.LoadAsync(entries, context, cancellationToken).ConfigureAwait(false));
189189
}
190190

191191
LogSkillsLoadedTotal(this._logger, skills.Count);

dotnet/src/Microsoft.Agents.AI.Mcp/Skills/Loaders/ArchiveEntryLoader.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,7 @@ public ArchiveEntryLoader(McpClient client, AgentMcpSkillsSourceOptions? options
5050
public string EntryType => "archive";
5151

5252
/// <inheritdoc/>
53-
public async Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry> entries, CancellationToken cancellationToken)
53+
public async Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry> entries, AgentSkillsSourceContext context, CancellationToken cancellationToken)
5454
{
5555
// Filter out entries that are missing required fields or have invalid names.
5656
var archiveEntries = this.FilterValidEntries(entries);
@@ -81,7 +81,7 @@ public async Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry>
8181
// Delegate discovery of extracted content to a file-based skills source.
8282
AgentFileSkillsSource fileSource = this.CreateFileSkillsSource(skillDirectories);
8383

84-
return await fileSource.GetSkillsAsync(cancellationToken).ConfigureAwait(false);
84+
return await fileSource.GetSkillsAsync(context, cancellationToken).ConfigureAwait(false);
8585
}
8686

8787
/// <summary>

dotnet/src/Microsoft.Agents.AI.Mcp/Skills/Loaders/IMcpSkillEntryLoader.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ internal interface IMcpSkillEntryLoader
3030
/// loaded successfully.
3131
/// </summary>
3232
/// <param name="entries">The index entries of this loader's <see cref="EntryType"/>. May be empty.</param>
33+
/// <param name="context">Contextual information about the agent and session requesting skills.</param>
3334
/// <param name="cancellationToken">A token to cancel the operation.</param>
34-
Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry> entries, CancellationToken cancellationToken);
35+
Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry> entries, AgentSkillsSourceContext context, CancellationToken cancellationToken);
3536
}

dotnet/src/Microsoft.Agents.AI.Mcp/Skills/Loaders/SkillMdEntryLoader.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ public SkillMdEntryLoader(McpClient client, ILoggerFactory loggerFactory)
2929
public string EntryType => "skill-md";
3030

3131
/// <inheritdoc/>
32-
public Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry> entries, CancellationToken cancellationToken)
32+
public Task<IList<AgentSkill>> LoadAsync(IReadOnlyList<McpSkillIndexEntry> entries, AgentSkillsSourceContext context, CancellationToken cancellationToken)
3333
{
3434
var skills = new List<AgentSkill>();
3535

dotnet/src/Microsoft.Agents.AI/CompatibilitySuppressions.xml

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,13 @@
8585
<Right>lib/net10.0/Microsoft.Agents.AI.dll</Right>
8686
<IsBaselineSuppression>true</IsBaselineSuppression>
8787
</Suppression>
88+
<Suppression>
89+
<DiagnosticId>CP0002</DiagnosticId>
90+
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseFilter(System.Func{Microsoft.Agents.AI.AgentSkill,System.Boolean})</Target>
91+
<Left>lib/net10.0/Microsoft.Agents.AI.dll</Left>
92+
<Right>lib/net10.0/Microsoft.Agents.AI.dll</Right>
93+
<IsBaselineSuppression>true</IsBaselineSuppression>
94+
</Suppression>
8895
<Suppression>
8996
<DiagnosticId>CP0002</DiagnosticId>
9097
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseScriptApproval(System.Boolean)</Target>
@@ -120,6 +127,13 @@
120127
<Right>lib/net10.0/Microsoft.Agents.AI.dll</Right>
121128
<IsBaselineSuppression>true</IsBaselineSuppression>
122129
</Suppression>
130+
<Suppression>
131+
<DiagnosticId>CP0002</DiagnosticId>
132+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(System.Threading.CancellationToken)</Target>
133+
<Left>lib/net10.0/Microsoft.Agents.AI.dll</Left>
134+
<Right>lib/net10.0/Microsoft.Agents.AI.dll</Right>
135+
<IsBaselineSuppression>true</IsBaselineSuppression>
136+
</Suppression>
123137
<Suppression>
124138
<DiagnosticId>CP0002</DiagnosticId>
125139
<Target>M:Microsoft.Agents.AI.AgentFileSkillScriptRunner.BeginInvoke(Microsoft.Agents.AI.AgentFileSkill,Microsoft.Agents.AI.AgentFileSkillScript,Microsoft.Extensions.AI.AIFunctionArguments,System.Threading.CancellationToken,System.AsyncCallback,System.Object)</Target>
@@ -204,6 +218,13 @@
204218
<Right>lib/net472/Microsoft.Agents.AI.dll</Right>
205219
<IsBaselineSuppression>true</IsBaselineSuppression>
206220
</Suppression>
221+
<Suppression>
222+
<DiagnosticId>CP0002</DiagnosticId>
223+
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseFilter(System.Func{Microsoft.Agents.AI.AgentSkill,System.Boolean})</Target>
224+
<Left>lib/net472/Microsoft.Agents.AI.dll</Left>
225+
<Right>lib/net472/Microsoft.Agents.AI.dll</Right>
226+
<IsBaselineSuppression>true</IsBaselineSuppression>
227+
</Suppression>
207228
<Suppression>
208229
<DiagnosticId>CP0002</DiagnosticId>
209230
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseScriptApproval(System.Boolean)</Target>
@@ -239,6 +260,13 @@
239260
<Right>lib/net472/Microsoft.Agents.AI.dll</Right>
240261
<IsBaselineSuppression>true</IsBaselineSuppression>
241262
</Suppression>
263+
<Suppression>
264+
<DiagnosticId>CP0002</DiagnosticId>
265+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(System.Threading.CancellationToken)</Target>
266+
<Left>lib/net472/Microsoft.Agents.AI.dll</Left>
267+
<Right>lib/net472/Microsoft.Agents.AI.dll</Right>
268+
<IsBaselineSuppression>true</IsBaselineSuppression>
269+
</Suppression>
242270
<Suppression>
243271
<DiagnosticId>CP0002</DiagnosticId>
244272
<Target>M:Microsoft.Agents.AI.AgentFileSkillScriptRunner.BeginInvoke(Microsoft.Agents.AI.AgentFileSkill,Microsoft.Agents.AI.AgentFileSkillScript,Microsoft.Extensions.AI.AIFunctionArguments,System.Threading.CancellationToken,System.AsyncCallback,System.Object)</Target>
@@ -323,6 +351,13 @@
323351
<Right>lib/net8.0/Microsoft.Agents.AI.dll</Right>
324352
<IsBaselineSuppression>true</IsBaselineSuppression>
325353
</Suppression>
354+
<Suppression>
355+
<DiagnosticId>CP0002</DiagnosticId>
356+
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseFilter(System.Func{Microsoft.Agents.AI.AgentSkill,System.Boolean})</Target>
357+
<Left>lib/net8.0/Microsoft.Agents.AI.dll</Left>
358+
<Right>lib/net8.0/Microsoft.Agents.AI.dll</Right>
359+
<IsBaselineSuppression>true</IsBaselineSuppression>
360+
</Suppression>
326361
<Suppression>
327362
<DiagnosticId>CP0002</DiagnosticId>
328363
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseScriptApproval(System.Boolean)</Target>
@@ -358,6 +393,13 @@
358393
<Right>lib/net8.0/Microsoft.Agents.AI.dll</Right>
359394
<IsBaselineSuppression>true</IsBaselineSuppression>
360395
</Suppression>
396+
<Suppression>
397+
<DiagnosticId>CP0002</DiagnosticId>
398+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(System.Threading.CancellationToken)</Target>
399+
<Left>lib/net8.0/Microsoft.Agents.AI.dll</Left>
400+
<Right>lib/net8.0/Microsoft.Agents.AI.dll</Right>
401+
<IsBaselineSuppression>true</IsBaselineSuppression>
402+
</Suppression>
361403
<Suppression>
362404
<DiagnosticId>CP0002</DiagnosticId>
363405
<Target>M:Microsoft.Agents.AI.AgentFileSkillScriptRunner.BeginInvoke(Microsoft.Agents.AI.AgentFileSkill,Microsoft.Agents.AI.AgentFileSkillScript,Microsoft.Extensions.AI.AIFunctionArguments,System.Threading.CancellationToken,System.AsyncCallback,System.Object)</Target>
@@ -442,6 +484,13 @@
442484
<Right>lib/net9.0/Microsoft.Agents.AI.dll</Right>
443485
<IsBaselineSuppression>true</IsBaselineSuppression>
444486
</Suppression>
487+
<Suppression>
488+
<DiagnosticId>CP0002</DiagnosticId>
489+
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseFilter(System.Func{Microsoft.Agents.AI.AgentSkill,System.Boolean})</Target>
490+
<Left>lib/net9.0/Microsoft.Agents.AI.dll</Left>
491+
<Right>lib/net9.0/Microsoft.Agents.AI.dll</Right>
492+
<IsBaselineSuppression>true</IsBaselineSuppression>
493+
</Suppression>
445494
<Suppression>
446495
<DiagnosticId>CP0002</DiagnosticId>
447496
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseScriptApproval(System.Boolean)</Target>
@@ -477,6 +526,13 @@
477526
<Right>lib/net9.0/Microsoft.Agents.AI.dll</Right>
478527
<IsBaselineSuppression>true</IsBaselineSuppression>
479528
</Suppression>
529+
<Suppression>
530+
<DiagnosticId>CP0002</DiagnosticId>
531+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(System.Threading.CancellationToken)</Target>
532+
<Left>lib/net9.0/Microsoft.Agents.AI.dll</Left>
533+
<Right>lib/net9.0/Microsoft.Agents.AI.dll</Right>
534+
<IsBaselineSuppression>true</IsBaselineSuppression>
535+
</Suppression>
480536
<Suppression>
481537
<DiagnosticId>CP0002</DiagnosticId>
482538
<Target>M:Microsoft.Agents.AI.AgentFileSkillScriptRunner.BeginInvoke(Microsoft.Agents.AI.AgentFileSkill,Microsoft.Agents.AI.AgentFileSkillScript,Microsoft.Extensions.AI.AIFunctionArguments,System.Threading.CancellationToken,System.AsyncCallback,System.Object)</Target>
@@ -561,6 +617,13 @@
561617
<Right>lib/netstandard2.0/Microsoft.Agents.AI.dll</Right>
562618
<IsBaselineSuppression>true</IsBaselineSuppression>
563619
</Suppression>
620+
<Suppression>
621+
<DiagnosticId>CP0002</DiagnosticId>
622+
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseFilter(System.Func{Microsoft.Agents.AI.AgentSkill,System.Boolean})</Target>
623+
<Left>lib/netstandard2.0/Microsoft.Agents.AI.dll</Left>
624+
<Right>lib/netstandard2.0/Microsoft.Agents.AI.dll</Right>
625+
<IsBaselineSuppression>true</IsBaselineSuppression>
626+
</Suppression>
564627
<Suppression>
565628
<DiagnosticId>CP0002</DiagnosticId>
566629
<Target>M:Microsoft.Agents.AI.AgentSkillsProviderBuilder.UseScriptApproval(System.Boolean)</Target>
@@ -596,6 +659,13 @@
596659
<Right>lib/netstandard2.0/Microsoft.Agents.AI.dll</Right>
597660
<IsBaselineSuppression>true</IsBaselineSuppression>
598661
</Suppression>
662+
<Suppression>
663+
<DiagnosticId>CP0002</DiagnosticId>
664+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(System.Threading.CancellationToken)</Target>
665+
<Left>lib/netstandard2.0/Microsoft.Agents.AI.dll</Left>
666+
<Right>lib/netstandard2.0/Microsoft.Agents.AI.dll</Right>
667+
<IsBaselineSuppression>true</IsBaselineSuppression>
668+
</Suppression>
599669
<Suppression>
600670
<DiagnosticId>CP0005</DiagnosticId>
601671
<Target>M:Microsoft.Agents.AI.AgentSkill.GetContentAsync(System.Threading.CancellationToken)</Target>
@@ -610,6 +680,13 @@
610680
<Right>lib/net10.0/Microsoft.Agents.AI.dll</Right>
611681
<IsBaselineSuppression>true</IsBaselineSuppression>
612682
</Suppression>
683+
<Suppression>
684+
<DiagnosticId>CP0005</DiagnosticId>
685+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(Microsoft.Agents.AI.AgentSkillsSourceContext,System.Threading.CancellationToken)</Target>
686+
<Left>lib/net10.0/Microsoft.Agents.AI.dll</Left>
687+
<Right>lib/net10.0/Microsoft.Agents.AI.dll</Right>
688+
<IsBaselineSuppression>true</IsBaselineSuppression>
689+
</Suppression>
613690
<Suppression>
614691
<DiagnosticId>CP0005</DiagnosticId>
615692
<Target>M:Microsoft.Agents.AI.AgentSkill.GetContentAsync(System.Threading.CancellationToken)</Target>
@@ -624,6 +701,13 @@
624701
<Right>lib/net472/Microsoft.Agents.AI.dll</Right>
625702
<IsBaselineSuppression>true</IsBaselineSuppression>
626703
</Suppression>
704+
<Suppression>
705+
<DiagnosticId>CP0005</DiagnosticId>
706+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(Microsoft.Agents.AI.AgentSkillsSourceContext,System.Threading.CancellationToken)</Target>
707+
<Left>lib/net472/Microsoft.Agents.AI.dll</Left>
708+
<Right>lib/net472/Microsoft.Agents.AI.dll</Right>
709+
<IsBaselineSuppression>true</IsBaselineSuppression>
710+
</Suppression>
627711
<Suppression>
628712
<DiagnosticId>CP0005</DiagnosticId>
629713
<Target>M:Microsoft.Agents.AI.AgentSkill.GetContentAsync(System.Threading.CancellationToken)</Target>
@@ -638,6 +722,13 @@
638722
<Right>lib/net8.0/Microsoft.Agents.AI.dll</Right>
639723
<IsBaselineSuppression>true</IsBaselineSuppression>
640724
</Suppression>
725+
<Suppression>
726+
<DiagnosticId>CP0005</DiagnosticId>
727+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(Microsoft.Agents.AI.AgentSkillsSourceContext,System.Threading.CancellationToken)</Target>
728+
<Left>lib/net8.0/Microsoft.Agents.AI.dll</Left>
729+
<Right>lib/net8.0/Microsoft.Agents.AI.dll</Right>
730+
<IsBaselineSuppression>true</IsBaselineSuppression>
731+
</Suppression>
641732
<Suppression>
642733
<DiagnosticId>CP0005</DiagnosticId>
643734
<Target>M:Microsoft.Agents.AI.AgentSkill.GetContentAsync(System.Threading.CancellationToken)</Target>
@@ -652,6 +743,13 @@
652743
<Right>lib/net9.0/Microsoft.Agents.AI.dll</Right>
653744
<IsBaselineSuppression>true</IsBaselineSuppression>
654745
</Suppression>
746+
<Suppression>
747+
<DiagnosticId>CP0005</DiagnosticId>
748+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(Microsoft.Agents.AI.AgentSkillsSourceContext,System.Threading.CancellationToken)</Target>
749+
<Left>lib/net9.0/Microsoft.Agents.AI.dll</Left>
750+
<Right>lib/net9.0/Microsoft.Agents.AI.dll</Right>
751+
<IsBaselineSuppression>true</IsBaselineSuppression>
752+
</Suppression>
655753
<Suppression>
656754
<DiagnosticId>CP0005</DiagnosticId>
657755
<Target>M:Microsoft.Agents.AI.AgentSkill.GetContentAsync(System.Threading.CancellationToken)</Target>
@@ -666,4 +764,11 @@
666764
<Right>lib/netstandard2.0/Microsoft.Agents.AI.dll</Right>
667765
<IsBaselineSuppression>true</IsBaselineSuppression>
668766
</Suppression>
767+
<Suppression>
768+
<DiagnosticId>CP0005</DiagnosticId>
769+
<Target>M:Microsoft.Agents.AI.AgentSkillsSource.GetSkillsAsync(Microsoft.Agents.AI.AgentSkillsSourceContext,System.Threading.CancellationToken)</Target>
770+
<Left>lib/netstandard2.0/Microsoft.Agents.AI.dll</Left>
771+
<Right>lib/netstandard2.0/Microsoft.Agents.AI.dll</Right>
772+
<IsBaselineSuppression>true</IsBaselineSuppression>
773+
</Suppression>
669774
</Suppressions>

dotnet/src/Microsoft.Agents.AI/Skills/AgentInMemorySkillsSource.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ public AgentInMemorySkillsSource(IEnumerable<AgentSkill> skills)
2828
}
2929

3030
/// <inheritdoc/>
31-
public override Task<IList<AgentSkill>> GetSkillsAsync(CancellationToken cancellationToken = default)
31+
public override Task<IList<AgentSkill>> GetSkillsAsync(AgentSkillsSourceContext context, CancellationToken cancellationToken = default)
3232
{
3333
return Task.FromResult<IList<AgentSkill>>(this._skills);
3434
}

dotnet/src/Microsoft.Agents.AI/Skills/AgentSkillsProvider.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -223,7 +223,7 @@ public AgentSkillsProvider(AgentSkillsSource source, AgentSkillsProviderOptions?
223223
/// <inheritdoc />
224224
protected override async ValueTask<AIContext> ProvideAIContextAsync(InvokingContext context, CancellationToken cancellationToken = default)
225225
{
226-
var skills = await this._source.GetSkillsAsync(cancellationToken).ConfigureAwait(false);
226+
var skills = await this._source.GetSkillsAsync(new AgentSkillsSourceContext(context.Agent, context.Session), cancellationToken).ConfigureAwait(false);
227227
if (skills is not { Count: > 0 })
228228
{
229229
return await base.ProvideAIContextAsync(context, cancellationToken).ConfigureAwait(false);

dotnet/src/Microsoft.Agents.AI/Skills/AgentSkillsProviderBuilder.cs

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -46,8 +46,9 @@ public sealed class AgentSkillsProviderBuilder
4646
private AgentSkillsProviderOptions? _options;
4747
private ILoggerFactory? _loggerFactory;
4848
private AgentFileSkillScriptRunner? _scriptRunner;
49-
private Func<AgentSkill, bool>? _filter;
49+
private Func<AgentSkill, AgentSkillsSourceContext, bool>? _filter;
5050
private bool _disableCaching;
51+
private CachingAgentSkillsSourceOptions? _cachingOptions;
5152

5253
/// <summary>
5354
/// Adds a file-based skill source that discovers skills from a filesystem directory.
@@ -189,7 +190,7 @@ public AgentSkillsProviderBuilder UseLoggerFactory(ILoggerFactory loggerFactory)
189190
/// </remarks>
190191
/// <param name="predicate">A predicate that determines which skills to include.</param>
191192
/// <returns>This builder instance for chaining.</returns>
192-
public AgentSkillsProviderBuilder UseFilter(Func<AgentSkill, bool> predicate)
193+
public AgentSkillsProviderBuilder UseFilter(Func<AgentSkill, AgentSkillsSourceContext, bool> predicate)
193194
{
194195
_ = Throw.IfNull(predicate);
195196
this._filter = predicate;
@@ -219,6 +220,19 @@ public AgentSkillsProviderBuilder DisableCaching()
219220
return this;
220221
}
221222

223+
/// <summary>
224+
/// Configures skill caching behavior.
225+
/// </summary>
226+
/// <param name="configure">A delegate to configure caching options.</param>
227+
/// <returns>This builder instance for chaining.</returns>
228+
public AgentSkillsProviderBuilder UseCachingOptions(Action<CachingAgentSkillsSourceOptions> configure)
229+
{
230+
_ = Throw.IfNull(configure);
231+
this._cachingOptions ??= new CachingAgentSkillsSourceOptions();
232+
configure(this._cachingOptions);
233+
return this;
234+
}
235+
222236
/// <summary>
223237
/// Builds the <see cref="AgentSkillsProvider"/>.
224238
/// </summary>
@@ -243,7 +257,7 @@ public AgentSkillsProvider Build()
243257

244258
if (!this._disableCaching)
245259
{
246-
source = new CachingAgentSkillsSource(source);
260+
source = new CachingAgentSkillsSource(source, this._cachingOptions);
247261
}
248262

249263
// Apply user-specified filter, then dedup.

dotnet/src/Microsoft.Agents.AI/Skills/AgentSkillsSource.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,8 @@ public abstract class AgentSkillsSource
1818
/// <summary>
1919
/// Gets the skills provided by this source.
2020
/// </summary>
21+
/// <param name="context">Contextual information about the agent and session requesting skills.</param>
2122
/// <param name="cancellationToken">Cancellation token.</param>
2223
/// <returns>A collection of skills from this source.</returns>
23-
public abstract Task<IList<AgentSkill>> GetSkillsAsync(CancellationToken cancellationToken = default);
24+
public abstract Task<IList<AgentSkill>> GetSkillsAsync(AgentSkillsSourceContext context, CancellationToken cancellationToken = default);
2425
}

0 commit comments

Comments
 (0)