using System.Text.Json; using Tiku.Application.Learning; using Tiku.Domain.Common; using Tiku.Domain.Learning; namespace Tiku.UnitTests.Learning; public sealed class QuestionGraderTests { [Fact] public void Choice_requires_exactly_one_matching_index() { var result = Grade("choice", 1, selected: [1]); Assert.Equal(AnswerGradingStatus.Correct, result.Status); Assert.True(result.IsCorrect); Assert.Equal(5, result.AwardedScore); } [Fact] public void Multiple_choice_compares_deduplicated_unordered_sets() { var result = Grade( "multiple_choice", correctIndices: JsonSerializer.SerializeToElement(new[] { 2, 0 }), selected: [0, 2, 2]); Assert.Equal(AnswerGradingStatus.Correct, result.Status); } [Theory] [InlineData("对", "true")] [InlineData("false", "错")] public void True_false_normalizes_supported_boolean_values(string expected, string actual) { var result = Grade("true_false", correctText: expected, answerText: actual); Assert.Equal(AnswerGradingStatus.Correct, result.Status); } [Fact] public void Fill_blank_normalizes_unicode_case_and_whitespace() { var rules = JsonSerializer.SerializeToElement(new { acceptedAnswers = new[] { "Entity Framework" } }); var result = Grade("fill_blank", correctText: "EF Core", answerText: " ENTITY FRAMEWORK ", rules: rules); Assert.Equal(AnswerGradingStatus.Correct, result.Status); } [Theory] [InlineData("short_answer")] [InlineData("reading")] [InlineData("programming")] public void Subjective_questions_remain_pending_review(string type) { var result = Grade(type, answerText: "student answer"); Assert.Equal(AnswerGradingStatus.PendingReview, result.Status); Assert.Null(result.IsCorrect); Assert.Null(result.AwardedScore); } private static QuestionGradingResult Grade( string type, int? correctIndex = null, JsonElement? correctIndices = null, string? correctText = null, IReadOnlyCollection? selected = null, string? answerText = null, JsonElement? rules = null) { return QuestionGrader.Grade(new QuestionGradingInput( type, correctIndex, correctIndices ?? JsonDefaults.Array(), correctText, rules ?? JsonDefaults.Object(), selected, answerText, 5)); } }