Send FromForm Object between APIS C# - c#

I want to send an Object between apis
but my controller is waiting for this
public async Task<IActionResult> Post([FromForm]UserViewModel input, CancellationToken ct = default(CancellationToken))
How can I send that model as a FromForm?
My Current call:
var userContent = JsonConvert.SerializeObject(userRequest);
HttpRequestMessage request = new HttpRequestMessage
{
Method = HttpMethod.Post,
RequestUri = new Uri($"{_apiUrl}users"),
Content = new StringContent(userContent, Encoding.UTF8, "application/json")
};
var result = await _httpClient.SendAsync(request);
My model:
public class UserViewModel
{
public string name;
public string lastname;
public List<IFormFile> GalleryImages { get; set; }
}

Related

Send IFormFile to the rest endpoint using http client

I have endpoint which accepts IFormFile file
[HttpPost]
public async Task<ActionResult<MyResponse>> Post([FromRoute] MyRequest request, CancellationToken cancellationToken = default)
{
...
}
public class MyRequest
{
[FromForm]
public IFormFile File { get; set; }
[FromRoute(Name = "userId")]
public string UserId{ get; set; }
}
on the client side I have simple IFormFile
var bytes = Encoding.UTF8.GetBytes("This is a dummy file");
IFormFile file = new FormFile(new MemoryStream(bytes), 0, bytes.Length, "File", "dummy.txt");
how can I send this IFormFile to the above post endpoint using http
client?
What have I tried?
var url = "";
var streamContent = new StreamContent(file.OpenReadStream(), 4069);
var httpClient = new HttpClient();
await httpClient.PostAsync($"{url}", streamContent);
You should pass the streamContent into MultipartFormDataContent.
var streamContent = new StreamContent(file.OpenReadStream());
streamContent.Headers.ContentType = new MediaTypeHeaderValue(file.ContentType);
streamContent.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data")
{
Name = "file",
FileName = file.FileName
};
MultipartFormDataContent formData = new MultipartFormDataContent();
formData.Add(streamContent);
var httpClient = new HttpClient();
await httpClient.PostAsync($"{url}", formData);
Demo

How to call a POST-action in a API-controller?

I don't know how send values strings or models to a HttpPost-action
I want to send a value to a HttpPost-action in a API.
He reach the HttpPost-action. But the value of parameter name is NULL.
What do I wrong?
By example the value of "name" = "Netherlands".
public async Task<long> UpdateCountry(string name)
{
string url = $"{myApi}/Address/UpdateCountry";
var model = JsonConvert.SerializeObject(new KeyValuePair<string, string>("name", name));
long id = await Post(url, model);
return id;
}
than the process starts in the BaseClass... in the function Post.
protected async Task<dynamic> Post(string url, string data)
{
var client = new HttpClient();
var httpContent = new StringContent(data);
HttpResponseMessage responseMessage = await client.PostAsync(url, httpContent);
var result = await responseMessage.Content.ReadAsStringAsync();
return JsonConvert.DeserializeObject<dynamic>(result);
}
And in the API the value of parameter name is NULL.
[HttpPost("UpdateCountry")]
public async Task<long> UpdateCountry(string name)
{
var countryId = _countryService.GetIdByName(name);
if (countryId == null)
{
var dto = new CountryDto() { Name = name };
....
countryId = await _countryService.Insert(dto);
}
else
{
dto.Name = name;
countryId = await _countryService.Update(dto);
}
return countryId.Value;
}
in the Client
public async Task<long> UpdateCountry(string name)
{
string url = $"{myApi}/Address/UpdateCountry";
var json = JsonConvert.SerializeObject(name);
long id = await Post(url, json, "text/json"); // or "application/json" when you use a model.
return id;
}
... and the BaseClass
protected async Task<dynamic> Post(string url, string data, string mediaType)
{
var client = new HttpClient();
var content = new StringContent(data, Encoding.UTF8, mediaType);
var response = await client.PostAsync(url, content);
if (response.IsSuccessStatusCode)
{
var result = await response.Content.ReadAsStringAsync();
return JsonConvert.DeserializeObject<dynamic>(result);
}
return null;
}
... and in the API
[HttpPost("UpdateCountry")]
public async Task<long> UpdateCountry([FromBody] string name)
{
var countryId = _countryService.GetIdByName(name);
if (!countryId.HasValue)
{
var dto = new CountryDto() { Name = name };
....
countryId = await _countryService.Insert(dto);
}
else
{
....
dto.Name = name;
countryId = await _countryService.Update(dto);
}
return countryId.Value;
}

Empty respond when Post data in C#

when I post username and password and IP address I got only an empty response.
my C# code is:
public async void APILogin(string user, string pass, string ip)
{
var person = new Userinfo { username = user, password = pass, ip = ip };
var json = JsonConvert.SerializeObject(person);
var data = new StringContent(json, Encoding.UTF8, "application/x-www-form-urlencoded");
var url = new Uri("http://localhost/login/dblogin.php") ;
HttpClient client = new HttpClient();
HttpResponseMessage response = await client.PostAsync(url,content:data);
HttpContent content = response.Content;
string myContent = await content.ReadAsStringAsync();
MessageBox.Show(myContent, "Info");
}
public class Userinfo
{
public String username { get; set; }
public String password { get; set; }
public String ip { get; set; }
}
I used this and it is worked.
var url = "http://localhost/login/dblogin.php";
HttpClient client = new HttpClient();
StringContent data = new StringContent("username="+user+"&password="+pass+"&ip="+ip);
data.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("application/x-www-form-urlencoded");
HttpResponseMessage response = await client.PostAsync(url, data);
response.EnsureSuccessStatusCode();
HttpContent content = response.Content;
string myContent = await content.ReadAsStringAsync();
loginResp apiResponse = JsonConvert.DeserializeObject<loginResp>(myContent);

Sending json response using Authentication filter in Web api controller?

I have an authentication filter in my controller
[ArcGISAuthentication]
I have defined the filter like below
public class ArcGISAuthenticationAttribute : Attribute, IAuthenticationFilter
{
public Task AuthenticateAsync(HttpAuthenticationContext context, CancellationToken cancellationToken)
{
return Task.Run(async () =>
{
var queryParameters = HttpUtility.ParseQueryString(context.Request.RequestUri.Query);
var token = queryParameters["token"];
if (!string.IsNullOrWhiteSpace(token))
{
var userInfo = await CommunityManager.GetUserInfoAsync(token);
context.Principal = new ArcGISUserPrincipal(userInfo, token);
context.Request.SetUserPrincipal(context.Principal);
}
else{
//What shoudld I do here to send a json response
}
});
}
public Task ChallengeAsync(HttpAuthenticationChallengeContext context, CancellationToken cancellationToken)
{
return Task.Run(() => { });
}
public ArcGISAuthenticationAttribute()
{
}
}
The problem is I want to send a json repsonse when the authentication fail. As in the else statement in the AuthenticateAsync above.
How can I do this?
Create a custom error result
public class ErrorResult : IHttpActionResult {
public ErrorResult(HttpRequestMessage request, string message, HttpStatusCode status = HttpStatusCode.InternalServerError, string reasonPhrase = "Internal Server Error") {
ReasonPhrase = reasonPhrase;
Request = request;
Message = message;
Status = status;
}
public HttpStatusCode Status { get; private set; }
public string ReasonPhrase { get; private set; }
public string Message { get; private set; }
public HttpRequestMessage Request { get; private set; }
public Task<HttpResponseMessage> ExecuteAsync(CancellationToken cancellationToken) {
return Task.FromResult(Execute());
}
private HttpResponseMessage Execute() {
var status = Status;
var responseBody = new Models.envelope {
meta = new Models.metadata {
code = (int)status,
type = ReasonPhrase ?? status.ToString().ToCamelCase(),
message = Message
},
data = null
};
var response = Request.CreateResponse(status, responseBody);
response.RequestMessage = Request;
response.ReasonPhrase = ReasonPhrase;
return response;
}
}
and set it to the context.Error property
if (!string.IsNullOrWhiteSpace(token))
{
var userInfo = await CommunityManager.GetUserInfoAsync(token);
context.Principal = new ArcGISUserPrincipal(userInfo, token);
context.Request.SetUserPrincipal(context.Principal);
}
else
{
context.Error = new ErrorResult(context.Request, "Some message to return");
}
In the Execute of the result you can set the response message to JSON or let the content negotiator determine what media type to return based on request headers.

Call HttpPut with parameter C#

So I create an HttpPut method in an ASP.NET web api.
[Route("api/Account/Save")]
[HttpPut]
public IHttpActionResult SaveAccount(Account acc) {
// do stuff
}
I pass in an instant of the Account class.
class Account
{
public int AccountID { get; set; }
public string AccountName { get; set; }
}
Now I want to call this from a console application. I am trying to do this but it's not working. It's not throwing any exception either.
var acc = new Account() { AccountID = 1234, AccountName = "zzzzP" };
string json = JsonConvert.SerializeObject(acc);
HttpContent content = new StringContent(json);
response = await client.PutAsync("api/Account/Save", content);
Json returned:
"{\"AccountID\":1234,\"AccountName\":\"zzzzP\"}"
You probably want something like this
static async Task PutAccount()
{
using (HttpClient client = new HttpClient())
{
client.BaseAddress = new Uri("http://yourWebSite.com");
var acc = new Account() { AccountID = 1234, AccountName = "zzzzP" };
string json = JsonConvert.SerializeObject(acc);
using (HttpResponseMessage response = await client.PutAsync("api/Account/Save", new StringContent(json)))
{
return response.EnsureSuccessStatusCode();
}
}
}

Categories