Using httpClient.postasync for web api calls .netcore

Viewed 3937

I am new to .netcore, I am working on web api that are running on docker container and while using postman the web api's are working really fine outputting the results. I want to make a program in .netcore calling the webapi endpoints and getting the response and using that particular response in other endpoints with MVC.

The explanation is given below. The default username and password for admin is default set for example username:admin , password: helloworld . The first time admin login the api requires a new personal password as shown in the Postman figure below.

The login api is: localhost://..../v1/users/login Login Admin

The first question is How to give the values in Authorization->BasicAuth using .netcore. The body of the api looks like the figure below. Setting new_password for Admin

After setting the new_password the response of the api is a token as given below. Token Generated

The particular token is then use in the Environment to create user. The image for more clear problem is given below. Token Save

Lastly, the token then used to make other API calls such as creating a user. API: https://localhost/..../v1/users The image is below. Creating a User

As a newbie in .netcore language, I am really struggling to do this kind of API calls, as most of the tutorials I tried are generating their own token from API, but here I just want to take the response token and save it and then use it in other API calls. The StackOverflow community's support was always really handy for me.

The Code I'm trying is given below.

**Controller**

 public class Login_AdminController : ControllerBase
    {
        [Route("/loginAdmin")]
        [HttpPost]
        public async Task<string> LoginAdminAsync([FromBody] dynamic content)
        {
            LoginAdmin L = new LoginAdmin();
            var client = new HttpClient();
            client.BaseAddress = new Uri("https://localhost:9090");
            var request = new HttpRequestMessage(HttpMethod.Post, "/v1/users/login");
            var byteArray = new UTF8Encoding().GetBytes($"<{L.username}:{L.df_Password}>");
            client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", Convert.ToBase64String(byteArray));

            var formData = new List<KeyValuePair<string, string>>();
            formData.Add(new KeyValuePair<string, string>("new_password", "helloWorld123!"));

            request.Content = new FormUrlEncodedContent(formData);
            var response = await client.SendAsync(request);
            Console.WriteLine(response);
            return content;
        }
   }
}
***Model***
    public class LoginAdmin
    {
        public string username = "admin";
        public string df_Password = "secret";
        public string new_Password { get; set; }
    }

Thank you.

2 Answers

Do you want to get token from response? If yes. Try this:

            var client = new HttpClient();
            client.BaseAddress = new Uri("http://localhost:12345/Api");
            var request = new HttpRequestMessage(HttpMethod.Post, "/token");

            var keyValues = new List<KeyValuePair<string, string>>();

            keyValues.Add(new KeyValuePair<string, string>("username", "yourusername"));
            keyValues.Add(new KeyValuePair<string, string>("password", "yourpassword"));

            request.Content = new FormUrlEncodedContent(keyValues);
            var response = client.SendAsync(request).Result;
            return response.Content.ReadAsStringAsync().Result;

Authorization is handled via the Authorization request header, which will include a token of some sort, prefixed by the scheme. What you're talking about here isn't really basic auth. With that, you literally pass the username and pass in the Authorization header with each request. What you're doing is just authenticating once to get an auth token, and then using that auth token to authorize further requests. In that scenario, you should really be posting the username and pass in the request body. Then, you'd do bearer auth with the token for the other requests, using the Authorization header. Still, to cover both bases:

Basic Auth

var token = Convert.ToBase64String(Encoding.UTF8.GetBytes($"{username}:{password}"));
request.Headers.Add("Authorization", $"Basic {token}");

Bearer Auth

request.Headers.Add("Authorization", $"Bearer {token}");
// where `token` is what was returned from your auth endpoint

FWIW, List<KeyValuePair<string, string>> is just Dictionary<string, string>. It's better to use the real type. Then, you can just do formData.Add("new_password", "helloWorld123!") instead of formData.Add(new KeyValuePair<string, string>("new_password", "helloWorld123!"))

Related