I am having trouble sending a list of objects to a webapi controller.
This is the controler:
[AcceptVerbs("POST")]
public string syncFoodData(List<intakeSync> str)
{
string apikey = Request.Headers.GetValues("api_key").ToArray()[0];
return "data syncronised";
}
This is the class:
public class intakeSync
{
public int memberID { get; set; }
public Double size { get; set; }
public string food { get; set; }
public string token { get; set; }
public string time { get; set; }
public string date { get; set; }
public string nocatch { get; set; }
public string calories { get; set; }
}
The value of str is always null.
this is the webmethod that sends the httprequest to the webapi
public static string syncIntakeData(string token, string[] syncString)
{
JavaScriptSerializer js = new JavaScriptSerializer();
List<intakeSync> str = new List<intakeSync>();
for (int i = 0; i <= syncString.Length - 1; i++)
{
str.Add(js.Deserialize<intakeSync>(syncString[i]));
}
string url = URI + "/api/Food/?str=" +js.Serialize(str);
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
request.Method = "POST";
request.ContentType = "application/x-www-form-urlencoded";
request.Headers.Add("api_key", token);
Stream requestStream = request.GetRequestStream();
StreamReader read = new StreamReader(request.GetResponse().GetResponseStream());
string dat = read.ReadToEnd();
read.Close();
request.GetResponse().Close();
return dat;
}
You can use this :
Request body in Json
[{id:1, nombre:"kres"},
{id:2, nombre:"cruz"}]
Api Rest .net C#
public string myFunction(IEnumerable<EntitySomething> myObj)
{
//...
return "response";
}
I don't know really how your JSON is serialized in the line js.Serialize(str); I suspect that this line is the core problem. Sending JSON is better suited in the POST Request body than in the query string. Anyways, I think that HttpClient is better suited for working with WebApi because it offers symmetric programming experience. You could try something like that with HttpClient :
using (var client = new HttpClient())
{
client.BaseAddress = new Uri(URI);
client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
client.DefaultRequestHeaders.Add("api_key", token);
var content = new ObjectContent(syncString, new JsonMediaTypeFormatter());
var result = client.PostAsync("/api/Food/", content).Result;
}
Related
I can get accesstoken but I don't know how to get username and uuid from accesstoken, when I login it's gave me something like that
{"accessToken":"123","clientToken":"123","selectedProfile":{"id":"123","name":"playername"},"availableProfiles":[{"id":"123","name":"playername"}]}
Thanks!
private vstrong textoid Signin_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
{
try
{
bool isSignedIn = false;
if (isSignedIn == true)
{
var request = (HttpWebRequest)WebRequest.Create("https://authserver.mojang.com/invalidate");
request.ContentType = "application/json";
request.Method = "POST";
using (var streamWriter = new StreamWriter(request.GetRequestStream()))
{
dynamic json = JsonConvert.SerializeObject(new
{
accessToken = Settings.Default.accessToken,
clientToken = Settings.Default.clientToken
});
}
Settings.Default.UUID = null;
Settings.Default.accessToken = null;
Settings.Default.clientToken = null;
}
else
{
var httpWebRequest = (HttpWebRequest)WebRequest.Create("https://authserver.mojang.com/authenticate");
httpWebRequest.ContentType = "application/json";
httpWebRequest.Method = "POST";
using (var streamWriter = new StreamWriter(httpWebRequest.GetRequestStream()))
{
dynamic json = JsonConvert.SerializeObject(new
{
agent = new
{
name = "Minecraft",
version = 1
},
username = email.Text,
password = password.Password
});
streamWriter.Write(json);
streamWriter.Flush();
streamWriter.Close();
}
var httpResponse = (HttpWebResponse)httpWebRequest.GetResponse();
using (var streamReader = new StreamReader(httpResponse.GetResponseStream()))
{
var result = streamReader.ReadToEnd();
ACCESS_TOKEN = result;
}
}
}
catch (WebException)
{
MessageBox.Show("Login failed. Invalid username or password.");
}
}
string ACCESS_TOKEN;
public string GetAccessToken()
{
return ACCESS_TOKEN;
}
That is a JSON response, which you will need to deserialize to use most effectively. You can do this with the following code:
var loginResponse = JsonConvert.DeserializeObject<LoginResponse>(result);
Now, the MinecraftLoginResponse will need to be a class you create yourself, unless there is a library that you are using for this. JSON consists of variable value combinations, the values after the ':', separated by commas. {} denote an object, and [] a collection.
In the minecraft response, you have two objects; the response itself, and then the Profile object. C# code of this response is:
public class Profile
{
public string id { get; set; }
public string name { get; set; }
}
public class LoginResponse
{
public string accessToken { get; set; }
public string clientToken { get; set; }
public Profile selectedProfile { get; set; }
public List<Profile> availableProfiles { get; set; }
}
I made the above by running the example response through this website, then removing the SelectedProfile and AvailableProfile as these are, logically, going to be the same thing. (Selected will be one of the available profiles).
I did a POST request code pointing to an API to do an automatic exchange program.
Here is the code:
string webAddr = "https://shapeshift.io/shift";
var httpWebRequest = (HttpWebRequest)WebRequest.Create(webAddr);
httpWebRequest.ContentType = "application/json; charset=utf-8";
httpWebRequest.Method = "POST";
using (var streamWriter = new StreamWriter(httpWebRequest.GetRequestStream()))
{
string json = "{ \"withdrawal\" : \"***ADDRESS WITH LETTER AND NUMBER***\", \"pair\" : \"eth_xmr\" }";
streamWriter.Write(json);
streamWriter.Flush();
}
var httpResponse = (HttpWebResponse)httpWebRequest.GetResponse();
using (var streamReader = new StreamReader(httpResponse.GetResponseStream()))
{
var responseText = streamReader.ReadToEnd();
Console.WriteLine(responseText);
}
And after executing the code, I'm getting this in the console
{"orderId":"1f90346c-c6d4-4d89-a24c-78b2bbdb6292","deposit":"0x534aa684274b4711f65b2d0e2e403cb169201255","depositType":"ETH","withdrawal":"***ADDRESS WITH LETTER AND NUMBER***","withdrawalType":"XMR"
Now, I want to put the address from deposit that I'm getting from the API into a string variable. I tried some code but I can't make it working. So how can I put this address in a string variable ?
You could deserialize the response and get from there that you want. In order to do so you could define a class, let's name it ApiResponse:
public class ApiResponse
{
[JsonProperty("orderId")]
public string orderId { get; set; }
[JsonProperty("deposit")]
public string deposit { get; set; }
[JsonProperty("depositType")]
public string depositType { get; set; }
[JsonProperty("withdrawal")]
public string withdrawal { get; set; }
[JsonProperty("withdrawalType")]
public string withdrawalType { get; set; }
}
and then after
var responseText = streamReader.ReadToEnd();
make the deserialization:
var apiResponse = JsonConvert.DeserializeObject<ApiResponse>(responseText);
I have used the Json.NET library. So if you haven't isntall it, you should do so or you could make use of another library and change correspondingly the above code.
I am trying to send a request from server side to my API, here is my code from Server
var httpWebRequest = (HttpWebRequest)WebRequest.Create("http://localhost:59606/api/values/UserCheck");
httpWebRequest.ContentType = "application/json; charset=utf-8";
httpWebRequest.Method = "POST";
using (var streamWriter = new StreamWriter(httpWebRequest.GetRequestStream()))
{
string json = "{\"username\":\"User\"," +
"\"password\":\"Mypassword\"," +
"\"logonfrom\":\"DOMAIN\\DomainName\"}";
streamWriter.Write(json);
streamWriter.Flush();
streamWriter.Close();
}
var httpResponse = (HttpWebResponse)httpWebRequest.GetResponse();
using (var streamReader = new StreamReader(httpResponse.GetResponseStream()))
{
var result = streamReader.ReadToEnd();
Console.WriteLine(result);
Console.ReadLine();
}
May API code are below:
[HttpPost]
[ActionName("UserCheck")]
public bool UserCheck([FromBody]User value)
{
ContextType CT = ContextType.Domain;
if (value.logonfrom.Split('\\')[0] == "DOMAIN")
{
CT = ContextType.Domain;
}else if(value.logonfrom.Split('\\')[0] == "MACHINE")
{
CT = ContextType.Machine;
}else
{
return false;
}
return CheckCredentials(value.username, value.password, CT,value.logonfrom.Split('\\')[1]);
}
when my request reach the Action of UserCheck, the value of
([FromBody]User value)
is null
my Class for the User is below
public class User
{
public string username { get; set; }
public string password { get; set; }
public string system { get; set; }
public string IP { get; set; }
public string logonfrom { get; set; }
}
BUT once i remove the logonfrom variable from json there is no error, i mean the parameter (value) successfully captures the content i sent.
Thanks
use the following peace of code.
string json = JsonConvert.SerializeObject(new { username = "afsa", password = "fsaf", system = "fsaf", ip = "fsf", logonfrom ="fsfsd"});
I am calling an external service using GetAsync() and passing parameters in query string. When i check the content in the response, i don't see anything returned, however it returns 200 OK and in fiddler it returns me the XML response correctly. I need the XML response to get de-serialize to an C# object and then further save it to DB.
Things tried:
1) Tried this by adding this setting in global- app_start(), It didn't help
GlobalConfiguration.Configuration.Formatters.XmlFormatter.UseXmlSerializer = true;
2) Created an object and tried to sent it via GetAysnc, that didn't help either.
public class Request
{
[XmlElement]
public string XML { get; set; }
[XmlElement]
public List<string> ProNumber { get; set; }
}
2) Should i try passing parameters in query string and expect json result? if i add mediatyperformatter to application/json?
Here is my code:
public async Task<HttpResponseMessage> GetData()
{
string requestString = "&xml=Y&PRONumber=82040X,03117X";
string result = "";
string url = #"http://my.yrc.com/dynamic/national/servlet?CONTROLLER=com.rdwy.ec.rextracking.http.controller.PublicTrailerHistoryAPIController";
try
{
using (var client = new HttpClient())
{
client.BaseAddress = new Uri(url);
client.DefaultRequestHeaders.Accept.Clear();
client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/xml"));
HttpResponseMessage response = await client.GetAsync(url+requestString);
if (response.IsSuccessStatusCode)
{
return response;
}
}
}
catch (Exception ex)
{
result = ex.Message;
}
return null;
}
EDIT:
Shipments scp = null;
XmlRootAttribute xRoot = new XmlRootAttribute();
xRoot.ElementName = "Shipment";
xRoot.IsNullable = true;
XmlSerializer serializer = new XmlSerializer(typeof(Shipment), xRoot);
using (Stream stream = response.Content.ReadAsStreamAsync().Result)
{
scp = (Shipments)serializer.Deserialize(stream);
}
Model:
public class Shipments
{
[XmlArrayItem(Type = typeof(Shipment))]
public Shipment[] Shipment;
}
public class Shipment
{
[XmlAttribute()]
public int returnCode { get; set; }
.................
..............
Getting error:<SHIPMENTS xmlns=''> was not expected.
Any help on this is much appreciated.
Thanks,
WH
This worked for me -
var client = new HttpClient();
var data = client.GetStringAsync("http://my.yrc.com/dynamic/national/servlet?CONTROLLER=com.rdwy.ec.rextracking.http.controller.PublicTrailerHistoryAPIController&xml=Y&PRONumber=82040X,03117X").Result;
var ser = new XmlSerializer(typeof(Shipments));
var t = (Shipments)ser.Deserialize(new StringReader(data));
public class Shipment
{
public string returnCode { get; set; }
public string returnMessage { get; set; }
public string freightBillNumber { get; set; }
//props
}
[XmlRoot(ElementName = "SHIPMENTS")]
public class Shipments
{
[XmlElement(ElementName = "SHIPMENT")]
public List<Shipment> SHIPMENT { get; set; }
}
EDIT
this works as well -
var data = client.GetStreamAsync("http://my.yrc.com/dynamic/national/servlet?CONTROLLER=com.rdwy.ec.rextracking.http.controller.PublicTrailerHistoryAPIController&xml=Y&PRONumber=82040X,03117X").Result;
EDIT
works as well -
var client = new HttpClient();
var data = client.GetAsync("http://my.yrc.com/dynamic/national/servlet?CONTROLLER=com.rdwy.ec.rextracking.http.controller.PublicTrailerHistoryAPIController&xml=Y&PRONumber=82040X,03117X").Result;
var ser = new XmlSerializer(typeof(Shipments));
var t = (Shipments)ser.Deserialize(data.Content.ReadAsStreamAsync().Result);
I am trying to test my Web API
[Test]
public void PolicyController_GetFirstPage_Successful()
{
using (var request = new HttpRequestMessage(HttpMethod.Get, "http://localhost/api/policies/~/~/0"))
{
using (var response = Client.SendAsync(request, CancellationToken.None).Result)
{
//blah blah
}
}
}
But my controller's action has [Authorize] attribute, so I am getting unauthorized error.
How can I handle this case?
First you need to get access token. And then you can send GET request with access token inside headers. You can read more about this here: http://msdn.microsoft.com/en-us/library/hh454950.aspx
Here is working console app example. It's quite hardcoded but works fine with my test app, so I hope it will be useful for you.
namespace ConsoleApplication
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("App started");
var tokenUrl = "http://localhost:29825/token";
var userName = "stack";
var userPassword = "password";
var request = string.Format("grant_type=password&username={0}&password={1}", HttpUtility.UrlEncode(userName), HttpUtility.UrlEncode(userPassword));
var token = HttpPost(tokenUrl, request);
var url = "http://localhost:29825/api/clients";
var clients = HttpGet(url, token.access_token);
foreach (var client in clients)
{
Console.WriteLine(client.Name);
}
Console.WriteLine("Press Enter to quit");
Console.ReadLine();
}
private static AccessToken HttpPost(string tokenUrl, string requestDetails)
{
WebRequest webRequest = WebRequest.Create(tokenUrl);
webRequest.ContentType = "application/x-www-form-urlencoded";
webRequest.Method = "POST";
byte[] bytes = Encoding.ASCII.GetBytes(requestDetails);
webRequest.ContentLength = bytes.Length;
using (Stream outputStream = webRequest.GetRequestStream())
{
outputStream.Write(bytes, 0, bytes.Length);
}
using (WebResponse webResponse = webRequest.GetResponse())
{
DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(AccessToken));
AccessToken token = (AccessToken)serializer.ReadObject(webResponse.GetResponseStream());
return token;
}
}
private static List<Client> HttpGet(string url, string token)
{
WebRequest webRequest = WebRequest.Create(url);
webRequest.ContentType = "application/x-www-form-urlencoded";
webRequest.Method = "GET";
webRequest.Headers.Add("Authorization", "Bearer " + token);
using (WebResponse webResponse = webRequest.GetResponse())
{
DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(List<Client>));
List<Client> clients = (List<Client>)serializer.ReadObject(webResponse.GetResponseStream());
return clients;
}
}
[DataContract]
public class AccessToken
{
[DataMember]
public string access_token { get; set; }
[DataMember]
public string token_type { get; set; }
[DataMember]
public string expires_in { get; set; }
[DataMember]
public string userName { get; set; }
}
[DataContract]
public class Client
{
[DataMember]
public string Id { get; set; }
[DataMember]
public string Name { get; set; }
}
}
}
I've just set Thread.CurrentPrincipal and it now works fine.