Skip to content

Commit cf47c58

Browse files
committed
Test cleanup
1 parent ce36a4f commit cf47c58

2 files changed

Lines changed: 58 additions & 103 deletions

File tree

test/Libraries/Microsoft.Extensions.AI.Abstractions.Tests/Utilities/AIJsonUtilitiesTests.cs

Lines changed: 38 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -564,6 +564,25 @@ static void TestMethod(int x, int y)
564564
Assert.Equal("Method description", descElement.GetString());
565565
}
566566

567+
[Fact]
568+
public static void CreateFunctionJsonSchema_AIFunctionNameAttribute_NotUsedForTitle()
569+
{
570+
[AIFunctionName("my_tool")]
571+
static void TestMethod(string param)
572+
{
573+
// Test method for schema generation
574+
}
575+
576+
var method = ((Action<string>)TestMethod).Method;
577+
JsonElement schema = AIJsonUtilities.CreateFunctionJsonSchema(method);
578+
579+
// The schema title is not derived from AIFunctionNameAttribute.
580+
if (schema.TryGetProperty("title", out JsonElement titleElement))
581+
{
582+
Assert.NotEqual("my_tool", titleElement.GetString());
583+
}
584+
}
585+
567586
[Fact]
568587
public static void CreateFunctionJsonSchema_DisplayNameAttribute_CanBeOverridden()
569588
{
@@ -584,11 +603,13 @@ static void TestMethod()
584603
[Fact]
585604
public static void CreateFunctionJsonSchema_AIParameterNameAttribute_UsedForPropertyName()
586605
{
587-
Delegate method = ([AIParameterName("custom_property_name")] string select, int top) =>
606+
static void TestMethod([AIParameterName("custom_property_name")] string select, int top)
588607
{
589-
};
608+
// Test method for schema generation
609+
}
590610

591-
JsonElement schema = AIJsonUtilities.CreateFunctionJsonSchema(method.Method);
611+
var method = ((Action<string, int>)TestMethod).Method;
612+
JsonElement schema = AIJsonUtilities.CreateFunctionJsonSchema(method);
592613

593614
JsonElement properties = schema.GetProperty("properties");
594615
Assert.True(properties.TryGetProperty("custom_property_name", out _));
@@ -602,51 +623,36 @@ public static void CreateFunctionJsonSchema_AIParameterNameAttribute_UsedForProp
602623
[Fact]
603624
public static void CreateFunctionJsonSchema_AIParameterNameAttribute_DuplicateNamesThrow()
604625
{
605-
Delegate duplicateByAttribute = ([AIParameterName("dup")] string first, [AIParameterName("dup")] string second) =>
626+
static void DuplicateByAttribute([AIParameterName("dup")] string first, [AIParameterName("dup")] string second)
606627
{
607-
};
608-
Assert.Throws<ArgumentException>(() => AIJsonUtilities.CreateFunctionJsonSchema(duplicateByAttribute.Method));
628+
// Test method for schema generation
629+
}
609630

610-
Delegate duplicateByCollision = ([AIParameterName("filter")] string select, string filter) =>
631+
Assert.Throws<ArgumentException>(() => AIJsonUtilities.CreateFunctionJsonSchema(((Action<string, string>)DuplicateByAttribute).Method));
632+
633+
static void DuplicateByCollision([AIParameterName("filter")] string select, string filter)
611634
{
612-
};
613-
Assert.Throws<ArgumentException>(() => AIJsonUtilities.CreateFunctionJsonSchema(duplicateByCollision.Method));
635+
// Test method for schema generation
636+
}
637+
638+
Assert.Throws<ArgumentException>(() => AIJsonUtilities.CreateFunctionJsonSchema(((Action<string, string>)DuplicateByCollision).Method));
614639
}
615640

616641
[Fact]
617642
public static void CreateFunctionJsonSchema_AIParameterNameAttribute_EscapesJsonPointerSegment()
618643
{
619644
JsonSerializerOptions options = new() { TypeInfoResolver = new DefaultJsonTypeInfoResolver() };
620-
Delegate method = ([AIParameterName("a/b~c")] RecursiveNode node) =>
645+
static void TestMethod([AIParameterName("a/b~c")] RecursiveNode node)
621646
{
622-
};
647+
// Test method for schema generation
648+
}
623649

624-
string schema = AIJsonUtilities.CreateFunctionJsonSchema(method.Method, serializerOptions: options).ToString();
650+
string schema = AIJsonUtilities.CreateFunctionJsonSchema(((Action<RecursiveNode>)TestMethod).Method, serializerOptions: options).ToString();
625651

626652
Assert.Contains("#/properties/a~1b~0c", schema);
627653
Assert.DoesNotContain("#/properties/a/b~c", schema);
628654
}
629655

630-
[Fact]
631-
public static void CreateFunctionJsonSchema_AIFunctionNameAttribute_NotUsedForSchemaTitle()
632-
{
633-
// AIFunctionNameAttribute overrides the AI-facing function name but does not affect the JSON schema title.
634-
Delegate method = [AIFunctionName("my_tool")] (string param) => { };
635-
636-
JsonElement schema = AIJsonUtilities.CreateFunctionJsonSchema(method.Method);
637-
638-
// The schema title is not derived from AIFunctionNameAttribute.
639-
Assert.False(schema.TryGetProperty("title", out JsonElement titleElement) && titleElement.GetString() == "my_tool");
640-
}
641-
642-
[Fact]
643-
public static void CreateFunctionJsonSchema_AIFunctionNameAttribute_HonoredByAIFunctionFactory()
644-
{
645-
Func<string> funcWithAttribute = [AIFunctionName("get_user")] () => "test";
646-
AIFunction func = AIFunctionFactory.Create(funcWithAttribute);
647-
Assert.Equal("get_user", func.Name);
648-
}
649-
650656
[Fact]
651657
public static void CreateJsonSchema_CanBeBoolean()
652658
{

test/Libraries/Microsoft.Extensions.AI.Tests/Functions/AIFunctionFactoryTest.cs

Lines changed: 20 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,7 @@ public async Task Parameters_MissingRequiredParametersFail_Async()
117117
AIFunctionFactory.Create((string? theParam) => theParam + " " + theParam),
118118
AIFunctionFactory.Create((int theParam) => theParam * 2),
119119
AIFunctionFactory.Create((int? theParam) => theParam * 2),
120+
AIFunctionFactory.Create(([AIParameterName("theParam")] string otherName) => otherName),
120121
];
121122

122123
foreach (AIFunction f in funcs)
@@ -335,19 +336,29 @@ public void Metadata_AIFunctionNameAttribute()
335336
Assert.Equal("options_name", func.Name);
336337
}
337338

339+
[Fact]
340+
public void Metadata_AIFunctionAndParameterNameAttributes_PreservedByAsDeclarationOnly()
341+
{
342+
AIFunction func = AIFunctionFactory.Create([AIFunctionName("my_tool")] ([AIParameterName("my_param")] string myParam) => myParam);
343+
344+
AIFunctionDeclaration declaration = func.AsDeclarationOnly();
345+
346+
Assert.Equal("my_tool", declaration.Name);
347+
Assert.Equal(func.JsonSchema.ToString(), declaration.JsonSchema.ToString());
348+
Assert.Contains("my_param", declaration.JsonSchema.ToString());
349+
Assert.IsNotAssignableFrom<AIFunction>(declaration);
350+
}
351+
338352
[Fact]
339353
public async Task Parameters_MappedByAIParameterNameAttribute_Async()
340354
{
341355
AIFunction func = AIFunctionFactory.Create(([AIParameterName("$select")] string select, int top) => select + top);
342356

343357
AssertExtensions.EqualFunctionCallResults("Name2", await func.InvokeAsync(new() { ["$select"] = "Name", ["top"] = 2 }));
344-
345-
ArgumentException ex = await Assert.ThrowsAsync<ArgumentException>(() => func.InvokeAsync(new() { ["top"] = 2 }).AsTask());
346-
Assert.Contains("$select", ex.Message);
347358
}
348359

349360
[Fact]
350-
public void AIParameterNameAttribute_OverridesSchemaPropertyName()
361+
public void Parameters_AIParameterNameAttribute_OverridesSchemaPropertyName()
351362
{
352363
AIFunction func = AIFunctionFactory.Create(
353364
([AIParameterName("my_param")] string myParam, int top) => myParam + top);
@@ -367,37 +378,7 @@ public void AIParameterNameAttribute_OverridesSchemaPropertyName()
367378
}
368379

369380
[Fact]
370-
public async Task AIParameterNameAttribute_BindsArgumentByOverriddenName_Async()
371-
{
372-
AIFunction func = AIFunctionFactory.Create(
373-
([AIParameterName("$select")] string select,
374-
[AIParameterName("$expand")] string expand,
375-
string filter) =>
376-
$"select='{select}', expand='{expand}', filter='{filter}'");
377-
378-
object? result = await func.InvokeAsync(new()
379-
{
380-
["$select"] = "Name,Id",
381-
["$expand"] = "Orders",
382-
["filter"] = "Active",
383-
});
384-
385-
AssertExtensions.EqualFunctionCallResults("select='Name,Id', expand='Orders', filter='Active'", result);
386-
}
387-
388-
[Fact]
389-
public async Task AIParameterNameAttribute_MissingRequiredArgument_ReportsSchemaName_Async()
390-
{
391-
AIFunction func = AIFunctionFactory.Create(
392-
([AIParameterName("my_param")] string myParam) => myParam);
393-
394-
ArgumentException ex = await Assert.ThrowsAsync<ArgumentException>(() => func.InvokeAsync().AsTask());
395-
396-
Assert.Contains("my_param", ex.Message);
397-
}
398-
399-
[Fact]
400-
public async Task AIParameterNameAttribute_HonoredByStrictUnmappedMemberHandling_Async()
381+
public async Task Parameters_AIParameterNameAttribute_StrictUnmappedMemberHandling_Async()
401382
{
402383
JsonSerializerOptions strictOptions = new(AIJsonUtilities.DefaultOptions)
403384
{
@@ -418,7 +399,7 @@ public async Task AIParameterNameAttribute_HonoredByStrictUnmappedMemberHandling
418399
}
419400

420401
[Fact]
421-
public async Task AIParameterNameAttribute_InheritedByOverride_Async()
402+
public async Task Parameters_AIParameterNameAttribute_InheritedByOverride_Async()
422403
{
423404
MethodInfo overrideMethod = typeof(MyDerivedType).GetMethod(nameof(MyDerivedType.Method))!;
424405
AIFunction func = AIFunctionFactory.Create(overrideMethod, new MyDerivedType());
@@ -430,31 +411,7 @@ public async Task AIParameterNameAttribute_InheritedByOverride_Async()
430411
}
431412

432413
[Fact]
433-
public async Task AIFunctionAndParameterNameAttributes_BothHonored_Async()
434-
{
435-
AIFunction func = AIFunctionFactory.Create([AIFunctionName("my_tool")] ([AIParameterName("my_param")] string myParam) => myParam);
436-
437-
Assert.Equal("my_tool", func.Name);
438-
Assert.Contains("my_param", func.JsonSchema.ToString());
439-
440-
AssertExtensions.EqualFunctionCallResults("Name", await func.InvokeAsync(new() { ["my_param"] = "Name" }));
441-
}
442-
443-
[Fact]
444-
public void AIFunctionAndParameterNameAttributes_NameAndParameterSchema_PreservedByAsDeclarationOnly()
445-
{
446-
AIFunction func = AIFunctionFactory.Create([AIFunctionName("my_tool")] ([AIParameterName("my_param")] string myParam) => myParam);
447-
448-
AIFunctionDeclaration declaration = func.AsDeclarationOnly();
449-
450-
Assert.Equal("my_tool", declaration.Name);
451-
Assert.Equal(func.JsonSchema.ToString(), declaration.JsonSchema.ToString());
452-
Assert.Contains("my_param", declaration.JsonSchema.ToString());
453-
Assert.IsNotAssignableFrom<AIFunction>(declaration);
454-
}
455-
456-
[Fact]
457-
public void AIParameterNameAttribute_EscapesNameInJsonPointerRef()
414+
public void Parameters_AIParameterNameAttribute_EscapesJsonPointerRef()
458415
{
459416
JsonSerializerOptions options = new(AIJsonUtilities.DefaultOptions) { TypeInfoResolver = new DefaultJsonTypeInfoResolver() };
460417

@@ -469,7 +426,7 @@ public void AIParameterNameAttribute_EscapesNameInJsonPointerRef()
469426
}
470427

471428
[Fact]
472-
public void AIParameterNameAttribute_DuplicateNames_Throw()
429+
public void Parameters_AIParameterNameAttribute_DuplicateNames_Throw()
473430
{
474431
ArgumentException ex = Assert.Throws<ArgumentException>(() => AIFunctionFactory.Create(
475432
([AIParameterName("dup")] string first, [AIParameterName("dup")] string second) => first + second));
@@ -481,7 +438,7 @@ public void AIParameterNameAttribute_DuplicateNames_Throw()
481438
}
482439

483440
[Fact]
484-
public void AIParameterNameAttribute_DuplicateNames_DetectedEvenWhenExcludedFromSchema()
441+
public void Parameters_AIParameterNameAttribute_DuplicateNames_ExcludedFromSchema()
485442
{
486443
// Validates that collision detection occurs in ExpectedArgumentNames collection
487444
// even when one of the colliding parameters is excluded from schema generation.
@@ -502,14 +459,6 @@ public void AIParameterNameAttribute_DuplicateNames_DetectedEvenWhenExcludedFrom
502459
Assert.Contains("AIParameterNameAttribute", ex.Message);
503460
}
504461

505-
[Fact]
506-
public void AIFunctionNameAttribute_DisplayNameAttribute_StillHonoredWhenNoAIFunctionNameAttribute()
507-
{
508-
AIFunction func = AIFunctionFactory.Create([DisplayName("from-display-name")] () => "result");
509-
510-
Assert.Equal("from-display-name", func.Name);
511-
}
512-
513462
[Fact]
514463
public void AIFunctionFactory_InheritedDescriptionAttributes_OnOverride()
515464
{

0 commit comments

Comments
 (0)