microsoft/semantic-kernel · error · InvalidDataException

Request failed: {nameof(GetUserProfileAsync)}

Error message

Request failed: {nameof(GetUserProfileAsync)}

What it means

An InvalidDataException thrown by GitHubPlugin.GetUserProfileAsync when JsonDocument.Deserialize<GitHubModels.User>() returns null. Because the GitHub /user response is a JSON object, a null result means the deserialization target mapping yielded null (empty/malformed body or incompatible shape), not a normal API error.

Source

Thrown at dotnet/samples/LearnResources/Plugins/GitHub/GitHubPlugin.cs:23

using Microsoft.SemanticKernel;

namespace Plugins;

internal sealed class GitHubSettings
{
    public string BaseUrl { get; set; } = "https://api.github.com";

    public string Token { get; set; } = string.Empty;
}

internal sealed class GitHubPlugin(GitHubSettings settings)
{
    [KernelFunction]
    public async Task<GitHubModels.User> GetUserProfileAsync()
    {
        using HttpClient client = this.CreateClient();
        JsonDocument response = await MakeRequestAsync(client, "/user");
        return response.Deserialize<GitHubModels.User>() ?? throw new InvalidDataException($"Request failed: {nameof(GetUserProfileAsync)}");
    }

    [KernelFunction]
    public async Task<GitHubModels.Repo> GetRepositoryAsync(string organization, string repo)
    {
        using HttpClient client = this.CreateClient();
        JsonDocument response = await MakeRequestAsync(client, $"/repos/{organization}/{repo}");

        return response.Deserialize<GitHubModels.Repo>() ?? throw new InvalidDataException($"Request failed: {nameof(GetRepositoryAsync)}");
    }

    [KernelFunction]
    public async Task<GitHubModels.Issue[]> GetIssuesAsync(
        string organization,
        string repo,
        [Description("default count is 30")]
        int? maxResults = null,
        [Description("open, closed, or all")]

View on GitHub (pinned to c028a0c7dc)

Solutions

  1. Check MakeRequestAsync throws on non-2xx and that the token (GitHubSettings.Token) is valid.
  2. Log the raw response body to see what was actually returned before deserialization.
  3. Confirm GitHubModels.User matches the current GitHub API schema.
  4. Handle null by returning a clearer error including status code and body.

Example fix

// before
return response.Deserialize<GitHubModels.User>() ?? throw new InvalidDataException($"Request failed: {nameof(GetUserProfileAsync)}");
// after - include status/body context
var user = response.Deserialize<GitHubModels.User>();
if (user is null) throw new InvalidDataException($"{nameof(GetUserProfileAsync)} returned non-deserializable body: {response.RootElement}");
return user;
Defensive patterns

Strategy: try-catch

Validate before calling

if (string.IsNullOrWhiteSpace(settings.Token)) throw new InvalidOperationException("GitHub token is not configured.");
if (!Uri.IsWellFormedUriString(settings.BaseUrl, UriKind.Absolute)) throw new InvalidOperationException("Invalid BaseUrl.");

Try / catch

try { return await plugin.GetUserProfileAsync(); }
catch (InvalidDataException ex) when (ex.Message.Contains(nameof(GitHubPlugin.GetUserProfileAsync))) { /* log raw body, verify token/scopes, surface to caller */ }

Prevention

When it happens

Trigger: Calling GetUserProfileAsync when the /user endpoint returns a body that deserializes to a null User object (empty body, unexpected JSON token, schema mismatch).

Common situations: Missing/invalid GitHub token causing a non-JSON error response; API schema change; network proxy returning an HTML error page; rate-limit body that does not map to User.

Related errors


AI-assisted analysis of microsoft/semantic-kernel@c028a0c7dc (2026-08-13). Data as JSON: /api/errors/47facc2bd2ab16cb. Report an issue: GitHub.