Как избежать необработанного исключения System.TypeLoadException в браузере при загрузке клиентского приложения Blazor

У меня есть клиентское приложение Blazor, и когда я пытаюсь запустить его для отладки из Visual Studio 2019 16.3.0 Preview 2.0, я получаю следующее сообщение об ошибке в браузере Chrome (при отладке с помощью Shift-Alt-D):

blazor.webassembly.js: 1 WASM: System.TypeLoadException: не удалось разрешить тип с токеном 01000020 из typeref (ожидаемый класс 'Microsoft.AspNetCore.Blazor.HttpClientJsonExtensions' в сборке 'Microsoft.AspNetCore.Blazor, версия =0.7.0.0, культура = нейтральный, PublicKeyToken=adb9793829ddae60')

Я установил точку останова как можно раньше в Main в Program.cs, но это не ударил.

Я использую Blazor версии 3.0.0-preview8.19405.7. Я искал решение этой проблемы, но все статьи, кажется, касаются других вопросов, кроме моей.

Кажется, проблема связана с Json и HttpClient, поэтому я подумал, что это может быть связано с обновлением, так как это было упомянуто в процедуре: https://devblogs.microsoft.com/aspnet/asp-net-core-and-blazor-updates-in-net-core-3-0-preview-8/

Но я фактически не использовал Json успешно до обновления (он находился в стадии разработки), поэтому я не знаю точно, имеет ли это какое-либо отношение к этому.

Редактировать: я попытался удалить две строки из кода (но сохранил ссылку на Microsoft.AspNetCore.Blazor.HttpClient в файле проекта):

result = await httpClient.GetJsonAsync<bool>("uri");

а также

await httpClient.PutJsonAsync("uri", value);

Это решило проблему, но без причины оставит меня без каких-либо звонков на мой сервер.

Итак, как я могу использовать httpClient? Или какие у меня есть альтернативы?

Редактировать:

Я создаю httpClient с помощью внедрения зависимостей в моем конструкторе

public class ServiceProxy : IServiceProxy
{
    private readonly HttpClient httpClient;
    public ServiceProxy(IHttpClientFactory httpClientFactory)
    {
        httpClient = httpClientFactory.CreateClient();
        httpClient.BaseAddress = new Uri("https://localhost:12345"), UriKind.Absolute);
    }

    public async Task<bool> GetResultAsync()
    {
        bool result
        try
        {
            result = await httpClient.GetJsonAsync<bool>("resource");
        }
        catch (HttpRequestException httpRequestException)
        {
            throw new ConnectionException(string.Format("Http Request failed: {0}", httpRequestException.Message), httpRequestException);
        }
        return result;
    }
}

Зависимости вводятся из моего класса запуска

public class Startup
{
    public void ConfigureServices(IServiceCollection services)
    {
        services.AddHttpClient();
        services.AddTransient<IServiceProxy, ServiceProxy>();
    }
}

2 ответа

Я обнаружил основную причину этой проблемы и тем самым нашел ее решение.

Я обновил свой Visual Studio 2019 до 16.4.0 Preview 1.0, а потом что-то сломалось, чего не ломалось раньше. И при консолидации моих зависимостей NuGet я был очень удивлен, что один из моих проектов зависимостей.NET Standard действительно имел ссылку на Blazor 0.7.0, который был старше, чем версия Preview 8, с которой я обновлялся.

Эта ссылка, вероятно, была причиной моей боли! Когда эта ссылка была удалена, я больше не мог вызывать свои httpClient.PutJsonAsync и httpClient.GetJsonAsync, потому что это, вероятно, реализовано только в версии HttpClient для Blazor.

Я переписал свою библиотеку, чтобы использовать httpClient.PutAsync и httpClient.GetAsync и использовать Newtonsoft.Json для сериализации и десериализации. Кроме того, после исправления некоторых проблем CORS это сработало.

Когда я сталкиваюсь с подобными проблемами, я удаляю папки bin и obj, пока мой проект закрыт. Я также удаляю все пакеты nuget и устанавливаю их снова.

Надеюсь, это поможет.

Blazor на стороне клиента не поддерживает IHttpClientFactory, Сторона клиента HttpClient не совпадает с серверной или другой версией. Это обертка XMLHttpRequest в браузере. (Дополнительно наслоен поверх машинописи)

[Клиентские приложения Blazor вызывают веб-API с помощью предварительно настроенной службы HttpClient. Составлять запросы, которые могут включать параметры JavaScript Fetch API, используя помощники Blazor JSON или HttpRequestMessage.

Серверные приложения Blazor вызывают веб-API с использованием экземпляров HttpClient, обычно создаваемых с использованием IHttpClientFactory. Для получения дополнительной информации см. Создание HTTP-запросов с использованием IHttpClientFactory в ASP.NET Core.] 1

На стороне клиента HttpClient это из коробки, включенной в DI. Вы можете использовать это, чтобы сделать http-звонки.

Вставьте его в код конструктора:

private readonly HttpClient _httpClient;

public YourClassName(HttpClient httpClient)
{
    _httpClient = httpClient;
}

//Use the _httpClient in other methods as usual

Инъекция в собственность

[Inject]
public HttpClient MyHttpClient { get; set; }

Внедрение на страницу блейзора

@inject HttpClient MyHttpClient

code {
   //Use the MyHttpClientin other methods as usual
}

Дополнительные ресурсы для DI в Blazor

Другие вопросы по тегам