// Copyright (c) Microsoft. All rights reserved. using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Threading; using System.Threading.Tasks; using Microsoft.Shared.DiagnosticIds; using Microsoft.Shared.Diagnostics; namespace Microsoft.Agents.AI; /// /// An discovered from a filesystem directory backed by a SKILL.md file. /// [Experimental(DiagnosticIds.Experiments.AgentsAIExperiments)] public sealed class AgentFileSkill : AgentSkill { private readonly IReadOnlyList _resources; private readonly IReadOnlyList _scripts; private readonly string _originalContent; private string? _content; /// /// Initializes a new instance of the class. /// /// The parsed frontmatter metadata for this skill. /// The full raw SKILL.md file content including YAML frontmatter. /// Absolute path to the directory containing this skill. /// Resources discovered for this skill. /// Scripts discovered for this skill. internal AgentFileSkill( AgentSkillFrontmatter frontmatter, string content, string path, IReadOnlyList? resources = null, IReadOnlyList? scripts = null) { this.Frontmatter = Throw.IfNull(frontmatter); this._originalContent = Throw.IfNull(content); this.Path = Throw.IfNullOrWhitespace(path); this._resources = resources ?? []; this._scripts = scripts ?? []; } /// public override AgentSkillFrontmatter Frontmatter { get; } /// /// /// Returns the raw SKILL.md content. When the skill has scripts, a /// <script_schemas> block is appended describing the argument format. /// The result is cached after the first access. /// public override ValueTask GetContentAsync(CancellationToken cancellationToken = default) { var content = this._content ??= this._scripts is { Count: > 0 } ? this._originalContent + AgentInlineSkillContentBuilder.BuildScriptSchemasBlock(this._scripts) : this._originalContent; return new(content); } /// /// Gets the directory path where the skill was discovered. /// public string Path { get; } /// public override ValueTask GetResourceAsync(string name, CancellationToken cancellationToken = default) { var resource = this._resources.FirstOrDefault(r => r.Name == name); return new(resource); } /// public override ValueTask GetScriptAsync(string name, CancellationToken cancellationToken = default) { var script = this._scripts.FirstOrDefault(s => s.Name == name); return new(script); } }