Box.com Get Request RestSharp C# - c#

I have a problem where my POST request returns back a token but when I change my code to use the token and try a GET request, it gives me a "Status:0" message. Am I writing this code wrong? I've tried adding "Bearer " + token to the Authentication.
ErrorException = {"Cannot send a content-body with this verb-type."}
Post:
var client = new RestClient("https://api.box.com/oauth2/token");
RestRequest request = new RestRequest() { Method = Method.Post };
request.AddHeader("Content-Type", "application/x-www-form-urlencoded");
request.AddParameter("client_id", $"{client_ID}");
request.AddParameter("client_secret", $"{client_secret}");
request.AddParameter("grant_type", "client_credentials");
request.AddParameter("box_subject_type", "enterprise");
request.AddParameter("box_subject_id", enterpriseID);
var response = await client.ExecuteAsync(request);
var responseMessage = JObject.Parse(response.Content);
GET:
var client2 = new RestClient("https://api.box.com/2.0/files/154072314030");
var request2 = new RestRequest() { Method = Method.Get };
request2.AddHeader("Authorization", token);
request2.AddHeader("Content-Type", "application/json");
var response2 = await client2.ExecuteAsync(request2);
var responseMessage2 = JObject.Parse(response2.Content);

Ended up using their SDK. This is how I was able to login and pull the items in the folder:
BoxFolder folderWithLink = new BoxFolder();
BoxSharedLinkRequest linkRequest = new BoxSharedLinkRequest();
int offset = 0;
int count = 0;
string folderID = "";
//create connection to Box.com
var boxConfig = new BoxConfigBuilder("CLIENT ID", "CLIENT SECRET", "Enterprise ID", "PRIVATE KEY", "PRIVATE KEY PASSWORD", "PUBLIC KEY ID").Build();
var boxJWT = new BoxJWTAuth(boxConfig);
var adminToken = await boxJWT.AdminTokenAsync();
var client = boxJWT.AdminClient(adminToken);
//Get the parent folder information and find the Batch folderID
while (folderID == "")
{
var batches = await client.FoldersManager.GetFolderItemsAsync("FOLDER ID", 250, offset);
foreach (var batchEntry in batches.Entries)
{
Console.Writeline(Batch.Name);
}

Related

Send email with attachemtns using Microsoft Graph Client API

I am trying to send an email with an attachment using Microsoft Graph Client API. I am getting the below exception:
{"error":{"code":"RequestBodyRead","message":"Cannot read the value '0' as a quoted JSON string value."}}
My code:
public bool SendWithAttachment(string emailSubject, string emailBody, string toEmail, string toName)
{
var token = AcquireToken(AppConstants.TenantId, AppConstants.EmailClientId, AppConstants.EmailClientSecret, AppConstants.UserId, AppConstants.Password);
try
{
byte[] contentBytes = System.IO.File.ReadAllBytes(#"C:\Users\user\Downloads\test\test.png");
string contentType = "image/png";
MessageAttachmentsCollectionPage attachments = new MessageAttachmentsCollectionPage();
attachments.Add(new FileAttachment
{
ODataType = "#microsoft.graph.fileAttachment",
ContentBytes = contentBytes,
ContentType = contentType,
ContentId = "testing",
Name = "testing.png"
});
var recipient = new Recipient
{
EmailAddress = new EmailAddress
{
Address = toEmail,
Name = toName
},
};
var message = new Message
{
Subject = emailSubject,
Body = new ItemBody
{
ContentType = BodyType.Text,
Content = emailBody
},
Attachments = attachments,
ToRecipients = new List<Recipient>() { recipient },
BccRecipients= new List<Recipient>()
};
var body = JsonConvert.SerializeObject(new { message = message });
var client = new RestClient();
var request = new RestRequest($"https://graph.microsoft.com/v1.0/users/{AppConstants.UserId}/sendMail", Method.Post);
request.AddHeader("Content-Type", $"application/json");
request.AddHeader("Authorization", $"Bearer {token}");
request.AddHeader("Cache-Control", $"no-cache");
request.AddParameter("application/json", body, ParameterType.RequestBody);
var restResponse = client.Execute(request);
return restResponse.StatusCode == HttpStatusCode.Accepted;
}
catch (Exception ex)
{
return false;
}
}
The exception seems very irrelevant to me. I think it's pointing to email body content type. Any suggestion would be very helpful.
Using graph SDK may help narrow down the issue like Eric said, since you already had the Bearer token, I think you can try my code below, I can use it to query user information, that why I set a User.ReadWrite permission for access token, but you already had the access token, so just using your token into the code:
var accessToken = await _tokenAcquisition.GetAccessTokenForUserAsync(new string[] { "User.ReadWrite.All" });
var authProvider = new DelegateAuthenticationProvider(async (request) => {
request.Headers.Authorization =
new System.Net.Http.Headers.AuthenticationHeaderValue("Bearer", accessToken);
});
var graphClient = new GraphServiceClient(authProvider);
var user = await graphClient.Me.Request().GetAsync();
//use this line to send email
await graphClient.Me.SendMail(message, null).Request().PostAsync();
By the way, I used this code to send email without the attachment before, not sure if it could help you...
var jsonStr = JsonSerializer.Serialize(temp);
string token = "your_token";
var httpClient = new HttpClient();
httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", token);
HttpResponseMessage response = await httpClient.PostAsync("https://graph.microsoft.com/v1.0/me/sendMail", new StringContent(jsonStr, Encoding.UTF8, "application/json"));

How to get reviews from Trustpilot API

Attempting to get Trustpilot reviews from a specific product but cannot get anywhere.
Can get the token with success but then the reviews:
Querying https://api.trustpilot.com/v1/private/product-reviews/business-units/{businessUnitId}/reviews would return no results at all but runs without error
AND
Querying https://api.trustpilot.com/v1/product-reviews/business-units/{businessUnitId}/reviews would return an error "Microsoft.VisualStudio.Services.OAuth.AccessTokenResponseProduct review retrieved.{"fault":{"faultstring":"Invalid ApiKey","detail":{"errorcode":"oauth.v2.InvalidApiKey"}}}"
The ApiKey is the same to get the token so do not understand why does not work here. In a desperate attempt added the token to the url (?token={token}) and also not successful.
The sku collection includes all variants. Also tried without sku parameter and nothing is retrieved.
Here is the code:
var ApiKey = "ApiKey";
var SecretKey = "SecretKey";
var Username = "Username";
var Password = "Password";
var serverUrl = "xxx.xxx.xxx.xxx";
var BusinnessUnit = "BusinnessUnit";
var AuthUrl2 = "https://api.trustpilot.com/v1/oauth/oauth-business-users-for-applications/accesstoken";
var ReviewUrl = "https://api.trustpilot.com/v1/private/product-reviews/business-units/"+ bkBusinnessUnit + "/reviews";
var ProductReviewUrl = "https://api.trustpilot.com/v1/product-reviews/business-units/" + bkBusinnessUnit + "/reviews";
var token = "";
// get token
using (var httpClient = new HttpClient())
{
try
{
httpClient.BaseAddress = new Uri(AuthUrl2);
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/x-www-form-urlencoded"));
var authString = ApiKey + ":" + SecretKey;
string encodedStr = Convert.ToBase64String(Encoding.UTF8.GetBytes(authString));
httpClient.DefaultRequestHeaders.Authorization = new System.Net.Http.Headers.AuthenticationHeaderValue("Basic", encodedStr);
var stringPayload = "grant_type=password&username=" + Username + "&password=" + Password;
var httpContent = new StringContent(stringPayload, Encoding.UTF8, "application/x-www-form-urlencoded");
HttpResponseMessage httpResponseMessage = httpClient.PostAsync(AuthUrl2, httpContent).Result;
var accessTokenResponseString = httpResponseMessage.Content.ReadAsStringAsync().Result;
var accessTokenResponseObject = JsonConvert.DeserializeObject<AccessTokenResponse>(accessTokenResponseString);
token = accessTokenResponseObject.AccessToken;
Console.WriteLine("Token retrieved. " + token);
}
catch (Exception ex)
{
Console.WriteLine("Failed!" + ex.ToString());
}
}
// get product reviews
using (var httpClient = new HttpClient())
{
try
{
httpClient.BaseAddress = new Uri(ProductReviewUrl);
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/x-www-form-urlencoded"));
var authString = ApiKey + ":" + SecretKey;
string encodedStr = Convert.ToBase64String(Encoding.UTF8.GetBytes(authString));
httpClient.DefaultRequestHeaders.Authorization = new System.Net.Http.Headers.AuthenticationHeaderValue("Basic", encodedStr);
var stringPayload = "sku=SK40132-BLK-6,SK40132-BLK-8,SK40132-BLK-10,SK40132-BLK-12,SK40132-BLK-14,SK40132-BLK-16,SK40132-BLK-18&token=" + token;
var httpContent = new StringContent(stringPayload, Encoding.UTF8, "application/x-www-form-urlencoded");
HttpResponseMessage httpResponseMessage = httpClient.PostAsync(ProductReviewUrl, httpContent).Result;
var reviewResponseString = httpResponseMessage.Content.ReadAsStringAsync().Result;
var reviewResponseObject = JsonConvert.DeserializeObject<AccessTokenResponse>(reviewResponseString);
Console.WriteLine(reviewResponseObject + "Product review retrieved." + reviewResponseString);
}
catch (Exception ex)
{
Console.WriteLine("Failed!" + ex.ToString());
}
}
// get reviews
using (var httpClient = new HttpClient())
{
try
{
httpClient.BaseAddress = new Uri(ReviewUrl);
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/x-www-form-urlencoded"));
httpClient.DefaultRequestHeaders.Authorization = new System.Net.Http.Headers.AuthenticationHeaderValue("Bearer", token);
var stringPayload = "sku=SK40132-BLK-6,SK40132-BLK-8,SK40132-BLK-10,SK40132-BLK-12,SK40132-BLK-14,SK40132-BLK-16,SK40132-BLK-18";
var httpContent = new StringContent(stringPayload, Encoding.UTF8, "application/x-www-form-urlencoded");
HttpResponseMessage httpResponseMessage = httpClient.PostAsync(ReviewUrl, httpContent).Result;
var reviewResponseString = httpResponseMessage.Content.ReadAsStringAsync().Result;
var reviewResponseObject = JsonConvert.DeserializeObject<AccessTokenResponse>(reviewResponseString);
Console.WriteLine(reviewResponseObject + "Review retrieved." + reviewResponseString);
}
catch (Exception ex)
{
Console.WriteLine("Failed!" + ex.ToString());
}
}
/v1/private/product-reviews/business-units/{businessUnitId}/reviews endpoint requires token. It could be provided either via header or via query parameters. It works for you as you did it right.
/v1/product-reviews/business-units/{businessUnitId}/reviews endpoint only requires apikey. You could pass it in two ways:
via header
httpClient.DefaultRequestHeaders.Accept.Add("apikey", ApiKey);
via query parameters
var stringPayload = "sku=SK40132-BLK-6,SK40132-BLK-8,SK40132-BLK-10,SK40132-BLK-12,SK40132-BLK-14,SK40132-BLK-16,SK40132-BLK-18&apikey=" + ApiKey;
It was incredible simple it should be a GetAsync instead of a PostAsync.
Thanks anyway for looking at it.

Sending Data to SalesForce by HttpClient(C#) Post Method, Not Working

I am trying to send a json Object to SalesFroce using HttpClient, but this behaves Weirdly...
First i login in to Salesforce Via following code
var sendPaylod = new Dictionary<string, string>
{
{"grant_type","password"},
{"client_id",s_clientId},
{"client_secret",s_clientSecrate},
{"username",s_username},
{"password",s_password}
};
HttpClient auth = new HttpClient();
HttpContent content = new FormUrlEncodedContent(sendPaylod);
HttpResponseMessage response = await auth.PostAsync(s_tokenRequestEndpointUrl, content);
string msg = await response.Content.ReadAsStringAsync();
Console.WriteLine(msg);
string authToken = (String)jsonObj["access_token"];
Now I have got authToken as a bearer token to send data to salesFroce
I am doing that by Following
var obj = new { Director = "003e000001MQYjB",
CityName = "XXAA",
CityId = "000000",
RegionName = "India",
RegionId = "00000" };
string c_url = "URL to which data will sent";
var c_Obj = JsonConvert.SerializeObject(obj);
var c_content = new System.Net.Http.StringContent(c_Obj, Encoding.UTF8, "application/json");
HttpClient c_client = new HttpClient();
c_client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Authorization","Bearer "+authToken);
HttpContent c_content = new StringContent(c_Obj, Encoding.UTF8, "application/json");
c_content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
var c_response = await c_client.PostAsync(c_url, content);
var c_msg = await c_response.Content.ReadAsStringAsync();
Now Am getting Following Response...
"status": "success",
"recordId": "",
"message": ""
If i Use Same Bearer Token in Postman and Send same Json Object I receive Following response.
"status": "success",
"recordId": "a16e0000002qV6aE",
"message": ""
Please Help in this matter.
Fix the next errors:
Change:
var c_response = await c_client.PostAsync(c_url, content);
to:
var contentType = new MediaTypeWithQualityHeaderValue("application/json");
c_client.DefaultRequestHeaders.Accept.Add(contentType);
var c_response = await c_client.PostAsync(c_url, c_content);
var c_msg = await c_response.Content.ReadAsStringAsync();
var result =JsonConvert.DeserializeObject<your return class>(c_msg);
and change your authorization to:
c_client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", authToken );

Replicate System.Net.Http method in RestSharp

I'm trying to replicate an example for calling a web API using RestSharp and I'm running into some issues.
Here is the example
string apiKey = "my key";
string apiSecret = "my secret";
string requestUri = "https://www.cryptopia.co.nz/Api/GetBalance";
var postData = new
{
Currency = "DOT"
};
// Create Request
var request = new HttpRequestMessage();
request.Method = HttpMethod.Post;
request.RequestUri = new Uri(requestUri);
request.Content = new ObjectContent(typeof(object), postData, new JsonMediaTypeFormatter());
// Authentication
string requestContentBase64String = string.Empty;
if (request.Content != null)
{
// Hash content to ensure message integrity
using (var md5 = MD5.Create())
{
requestContentBase64String = Convert.ToBase64String(md5.ComputeHash(await request.Content.ReadAsByteArrayAsync()));
}
}
//create random nonce for each request
var nonce = Guid.NewGuid().ToString("N");
//Creating the raw signature string
var signature = Encoding.UTF8.GetBytes(string.Concat(apiKey, HttpMethod.Post, HttpUtility.UrlEncode(request.RequestUri.AbsoluteUri.ToLower()), nonce, requestContentBase64String));
using (var hmac = new HMACSHA256(Convert.FromBase64String(apiSecret)))
{
request.Headers.Authorization = new AuthenticationHeaderValue("amx", string.Format("{0}:{1}:{2}", apiKey, Convert.ToBase64String(hmac.ComputeHash(signature)), nonce));
}
// Send Request
using (var client = new HttpClient())
{
var response = await client.SendAsync(request);
if (response.IsSuccessStatusCode)
{
Console.WriteLine(await response.Content.ReadAsStringAsync());
//{"Success":true,"Error":null,"Data":[{"CurrencyId":2,"Symbol":"DOT","Total":9646.07411016,"Available":9646.07411016,"Unconfirmed":0.0,"HeldForTrades":0.0,"PendingWithdraw":0.0,"Address":"1HEfio1kreDBgj5uCw4VHbEDSgc6YJXfTN","Status":"OK","StatusMessage":null}]}
}
}
I believe the issue I'm having is that the signature variable isn't being created properly. I'm setting the body of the RestSharp request using
request.AddJsonBody(request.JsonSerializer.Serialize(new { Currency = "DOT" }));
To get the body request.content I'm using
var body = request.Parameters.Where(p => p.Type == ParameterType.RequestBody).FirstOrDefault().Value.ToString();
To get the requestContentBase64String I'm using
var requestSignatureBase64String = Convert.ToBase64String(signatureBytes);
And finally to add the Authorization header I'm using
request.AddHeader("Authorization", $"amx {apiKey}:{requestSignatureBase64String}:{nonce}");
The response from the server is
"Success":false,"Error":"Signature does not match request parameters."

Twitter API invalid or expired token

I'm trying to use the below code but for some reason I'm getting an invalid or expired token it seemed to work once but never again.
Any ideas? (consumerKey and consumerSecret are constants generated in the class.)
public ActionResult Index()
{
string twitterAccount = System.Configuration.ConfigurationManager.AppSettings["twitterAccount"];
JsonDeserializer jsonDeserializer = new JsonDeserializer();
var model = new TwitterVM.LandingModel();
var qs = GetToken();
string oauthToken = qs["oauth_token"];
string oauthTokenSecret = qs["oauth_token_secret"];
RestClient client = new RestClient("https://api.twitter.com/1.1")
{
Authenticator = OAuth1Authenticator.ForProtectedResource(consumerKey, consumerSecret, oauthToken, oauthTokenSecret)
};
RestRequest request = new RestRequest("statuses/user_timeline", Method.GET);
request.Parameters.Add(new Parameter()
{
Name = "screen_name",
Value = twitterAccount,
Type = ParameterType.GetOrPost
});
request.Parameters.Add(new Parameter()
{
Name = "count",
Value = 10,
Type = ParameterType.GetOrPost
});
request.Parameters.Add(new Parameter()
{
Name = "include_rts",
Value = true,
Type = ParameterType.GetOrPost
});
request.Parameters.Add(new Parameter()
{
Name = "include_entities",
Value = true,
Type = ParameterType.GetOrPost
});
IRestResponse response = client.Execute(request);
model.Tweets =
jsonDeserializer.Deserialize<List<TwitterVM.Tweet>>(response);
return View(model);
}
private NameValueCollection GetToken()
{
RestClient client = new RestClient("https://api.twitter.com") { Authenticator = OAuth1Authenticator.ForRequestToken(consumerKey, consumerSecret) };
//Do the auth shit...
RestRequest request = new RestRequest("oauth/request_token", Method.POST);
IRestResponse response = client.Execute(request);
return HttpUtility.ParseQueryString(response.Content);
}
Using Twitter's OAuth2 API (https://api.twitter.com/oauth2/token)
See https://dev.twitter.com/oauth/application-only for details....
var client = await CreateHttpClient("....", "....");
//don't dispose this client and use for subsequent API calls
var screenName = "....";
var count = 10;
var include_rts = true;
var url = $"https://api.twitter.com/1.1/statuses/user_timeline.json?screen_name={screenName}&include_rts={include_rts}&count={count}";
var json = await client.GetStringAsync(url);
public static async Task<HttpClient> CreateHttpClient(string consumerKey, string consumerSecret)
{
var bearerToken = Convert.ToBase64String(Encoding.UTF8.GetBytes(consumerKey + ":" + consumerSecret));
string url = "https://api.twitter.com/oauth2/token";
HttpClient client = new HttpClient();
client.DefaultRequestHeaders.TryAddWithoutValidation("Authorization", "Basic " + bearerToken);
var resp = await client.PostAsync(url, new StringContent("grant_type=client_credentials", Encoding.UTF8, "application/x-www-form-urlencoded")).ConfigureAwait(false);
resp.EnsureSuccessStatusCode();
var result = await resp.Content.ReadAsStringAsync().ConfigureAwait(false);
var jObj = new JavaScriptSerializer().Deserialize<Dictionary<string,string>>(result);
if (jObj["token_type"] != "bearer") throw new Exception("Invalid Response From Twitter/OAuth");
client.DefaultRequestHeaders.Remove("Authorization");
client.DefaultRequestHeaders.TryAddWithoutValidation("Authorization", "Bearer " + jObj["access_token"]);
return client;
}

Categories

Resources