在运行时将值发送给Singleton

时间:2018-12-07 15:29:25

标签: c#

目前在Startup.cs中,我有:

services.AddSingleton<IApiClient>(new ApiClient(Configuration.GetValue<string>("WebApiBaseAddress")));

我有一个APIClient:

public class ApiClient : IApiClient
{
    private readonly HttpClient _client;
    private readonly JsonMediaTypeFormatter _formatter;

    /// <summary>
    /// The ApiClient constructor.
    /// </summary>
    public ApiClient(string baseAddress)
    {
        _client = new HttpClient { BaseAddress = new Uri(baseAddress) };
        _client.DefaultRequestHeaders.Accept.Clear();
        _client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
        //_client.DefaultRequestHeaders.Add("Authorization", "Bearer " + apiToken);

        _formatter = new JsonMediaTypeFormatter();
        _formatter.SerializerSettings.NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore;
    }

    /// <summary>
    /// Fetches the list of <see cref="TModel"/>. 
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <returns>List of <see cref="TModel"/>.</returns>
    public async Task<IList<TModel>> Get<TModel>(string path)
    {
        return await Get<TModel>(path, null);
    }

    public async Task<TModel> GetObject<TModel>(string path)
    {
        // todo : use parameters
        var response = await _client.GetStringAsync($"{path}");
        var result = JsonConvert.DeserializeObject<TModel>(response);

        return result;
    }

    /// <summary>
    /// Fetches the list of <see cref="TModel"/>. 
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="parameters">The uri parameters.</param>
    /// <returns>The list of <see cref="TModel"/>.</returns>
    private async Task<IList<TModel>> Get<TModel>(string path, IDictionary<string, string> parameters)
    {
        // todo : use parameters
        var response = await _client.GetStringAsync($"{path}");
        var result = JsonConvert.DeserializeObject<IList<TModel>>(response);

        return result;
    }

    /// <summary>
    /// Fetches the <see cref="TModel"/>. 
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="id">Unique identifier of the model.</param>
    /// <param name="afterPath">The uri path after id.</param>
    /// <returns>The <see cref="TModel"/> model.</returns>
    public async Task<TModel> Get<TModel>(string path, object id, string afterPath = null)
    {
        var response = await _client.GetStringAsync($"{path}/{id}{afterPath}");
        var result = JsonConvert.DeserializeObject<TModel>(response);

        return result;
    }

    /// <summary>
    /// Creates the <see cref="TModel"/> model.
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="model">The model.</param>
    public async Task<HttpResponseMessage> Post<TModel>(string path, TModel model)
    {
        HttpContent content = new ObjectContent<TModel>(model, _formatter);
        return await _client.PostAsync($"{path}", content);
    }

    /// <summary>
    /// Updates the <see cref="TModel"/> model.
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="id">Unique identifier of the model.</param>
    /// <param name="model">The model.</param>
    public async Task<HttpResponseMessage> Put<TModel>(string path, object id, TModel model)
    {
        HttpContent content = new ObjectContent<TModel>(model, _formatter);
        return await _client.PutAsync($"{path}/{id}", content);
    }

    /// <summary>
    /// Partially update the model
    /// </summary>
    /// <typeparam name="TModel"></typeparam>
    /// <param name="path"></param>
    /// <param name="id"></param>
    /// <param name="model"></param>
    /// <returns></returns>
    public async Task<HttpResponseMessage> Patch<TModel>(string path, object id, TModel model)
    {
        JsonPatchDocument patchDoc = new JsonPatchDocument();

        foreach (PropertyInfo propInfo in model.GetType().GetProperties())
        {
            var value = propInfo.GetValue(model);
            if (value == null) continue;
            patchDoc.Replace(propInfo.Name, value);
        }

        var serializedPatchItem = JsonConvert.SerializeObject(patchDoc);

        var method = new HttpMethod("PATCH");
        var request = new HttpRequestMessage(method, $"{path}/{id}")
        {
            Content = new StringContent(serializedPatchItem, System.Text.Encoding.Unicode, "application/json")
        };

        return await _client.SendAsync(request);
    }

    /// <summary>
    /// Deletes the model.
    /// </summary>
    /// <param name="path">The uri path.</param>
    /// <param name="id">Unique identifier of the model.</param>
    public async Task<HttpResponseMessage> Delete(string path, object id)
    {
        return await _client.DeleteAsync($"{path}/{id}");
    }
}
}

我有一个APIClient接口:

public interface IApiClient
{
    /// <summary>
    /// Fetches the list of <see cref="TModel"/>. 
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <returns>List of <see cref="TModel"/>.</returns>
    Task<IList<TModel>> Get<TModel>(string path);

    //
    Task<TModel> GetObject<TModel>(string path);

    /// <summary>
    /// Fetches the <see cref="TModel"/>. 
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="id">Unique identifier of the model.</param>
    /// <param name="afterPath">The uri path after id.</param>
    /// <returns>The <see cref="TModel"/> model.</returns>
    Task<TModel> Get<TModel>(string path, object id, string afterPath = null);

    /// <summary>
    /// Creates the <see cref="TModel"/> model.
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="model">The model.</param>
    Task<HttpResponseMessage> Post<TModel>(string path, TModel model);

    /// <summary>
    /// Updates the <see cref="TModel"/> model.
    /// </summary>
    /// <typeparam name="TModel">Model's type.</typeparam>
    /// <param name="path">The uri path.</param>
    /// <param name="id">Unique identifier of the model.</param>
    /// <param name="model">The model.</param>
    Task<HttpResponseMessage> Put<TModel>(string path, object id, TModel model);

    /// <summary>
    /// Partially updates the model
    /// </summary>
    /// <typeparam name="TModel"></typeparam>
    /// <param name="path"></param>
    /// <param name="id"></param>
    /// <param name="model"></param>
    /// <returns></returns>
    Task<HttpResponseMessage> Patch<TModel>(string path, object id, TModel model);

    /// <summary>
    /// Deletes the model.
    /// </summary>
    /// <param name="path">The uri path.</param>
    /// <param name="id">Unique identifier of the model.</param>
    Task<HttpResponseMessage> Delete(string path, object id);
}

因此,此刻将在启动时使用配置中的基址创建APIClient。

我想在运行时将另一个名为ApiToken的值传递给APIClient,并在用户成功登录后从我的登录控制器将其添加为Authorization标头。

我将从Auth控制器返回的API令牌存储在以下位置:

new Claim("Token", loggedInUser.ApiToken.ToString())

我将APIClient更改为:

public ApiClient(string baseAddress, string apiToken)

但是随着它在一开始就设置好,我不清楚用户登录后如何在运行时进行设置。

有人可以给我一些指示吗?

0 个答案:

没有答案