microsoft/teams.net

Public

mirrored fromhttps://github.com/microsoft/teams.netAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
91427f12753b43af544fcd5f77244b200b039c87

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

Libraries/Microsoft.Teams.AI/Function.cs

119lines · modecode

1// Copyright (c) Microsoft Corporation. All rights reserved.
2// Licensed under the MIT License.
3
4using System.Reflection;
5using System.Text.Json;
6using System.Text.Json.Nodes;
7using System.Text.Json.Serialization;
8
9using Json.Schema;
10
11using Microsoft.Teams.AI.Annotations;
12using Microsoft.Teams.AI.Messages;
13using Microsoft.Teams.Common.Extensions;
14using Microsoft.Teams.Common.Json;
15
16namespace Microsoft.Teams.AI;
17
18/// <summary>
19/// defines a block of code that
20/// can be called by a model
21/// </summary>
22[JsonConverter(typeof(TrueTypeJsonConverter<IFunction>))]
23public interface IFunction
24{
25 /// <summary>
26 /// the unique name
27 /// </summary>
28 public string Name { get; }
29
30 /// <summary>
31 /// a description of what the function
32 /// should be used for
33 /// </summary>
34 public string? Description { get; }
35
36 /// <summary>
37 /// the Json Schema representing what
38 /// parameters the function accepts
39 /// </summary>
40 public JsonSchema? Parameters { get; }
41}
42
43/// <summary>
44/// defines a block of code that
45/// can be called by a model
46/// </summary>
47public class Function : IFunction
48{
49 [JsonPropertyName("name")]
50 [JsonPropertyOrder(0)]
51 public string Name { get; set; }
52
53 [JsonPropertyName("description")]
54 [JsonPropertyOrder(1)]
55 public string? Description { get; set; }
56
57 [JsonPropertyName("parameters")]
58 [JsonPropertyOrder(2)]
59 public JsonSchema? Parameters { get; set; }
60
61 [JsonIgnore]
62 public Delegate Handler { get; set; }
63
64 public Function(string name, string? description, Delegate handler)
65 {
66 Name = name;
67 Description = description;
68 Handler = handler;
69 }
70
71 public Function(string name, string? description, JsonSchema? parameters, Delegate handler)
72 {
73 Name = name;
74 Description = description;
75 Parameters = parameters;
76 Handler = handler;
77 }
78
79 internal Task<object?> Invoke(FunctionCall call)
80 {
81 if (call.Arguments is not null && Parameters is not null)
82 {
83 var valid = Parameters.Evaluate(JsonNode.Parse(call.Arguments), new() { EvaluateAs = SpecVersion.DraftNext });
84
85 if (!valid.IsValid)
86 {
87 Console.WriteLine(JsonSerializer.Serialize(valid));
88 throw new ArgumentException(
89 string.Join("\n", valid.Errors?.Select(e => $"{e.Key} => {e.Value}") ?? [])
90 );
91 }
92 }
93
94 var args = call.Parse() ?? new Dictionary<string, object?>();
95 var method = Handler.GetMethodInfo();
96 var parameters = method.GetParameters().Select(param =>
97 {
98 var name = param.GetCustomAttribute<ParamAttribute>()?.Name ?? param.Name ?? param.Position.ToString();
99 args.TryGetValue(name, out var value);
100
101 if (value is JsonElement element)
102 {
103 return element.Deserialize(param.ParameterType);
104 }
105
106 return value;
107 }).ToArray();
108
109 return method.InvokeAsync(Handler.Target, parameters);
110 }
111
112 public override string ToString()
113 {
114 return JsonSerializer.Serialize(this, new JsonSerializerOptions()
115 {
116 WriteIndented = true
117 });
118 }
119}