handle StatusCode==302 when using HttpWebrequest - c# - c#-3.0

I have a windows app that I am trying to build to simulate an upload to a web app. The project is in C# 3.0.
When using Fiddler, I can see the following
/login page - 200 code
enter pwd/uname
/home page - 302 code
/home page - 200 code
/upload page [This page has simple multi-part form post where user can select at max 2 files to upload] - 200 code
/fileprocessed page - 302 code
/fileprocessed page - 200 code
When i use HttpWebrequest with webresponse object, i get
/login page - 200 code
enter pwd/uname
/home page - 200 code
/upload page [This page has simple multi-part form post where user can select at max 2 files to upload] - 200 code
/fileprocessed page - 302 code
I do have SetAutoRedirect to true
My code is
Stream requestStream = request.GetRequestStream();
requestStream.Write(bytes, 0, bytes.Length);
requestStream.Write(buffer, 0, buffer.Length);
FileStream stream2 = new FileStream(filePath, FileMode.Open, FileAccess.Read);
byte[] buffer = new byte[0x1000];
int count = 0;
while ((count = stream2.Read(buffer, 0, buffer.Length)) != 0)
{
requestStream.Write(buffer, 0, count);
}
bytes = Encoding.ASCII.GetBytes("\r\n--" + str2 + "--\r\n");
requestStream.Write(bytes, 0, bytes.Length);
requestStream.Close();
stream.Close();
HttpWebResponse response = request.GetResponse() as HttpWebResponse;
if(response.StatusCode == HttpStatusCode.Found)
{
string newURL = response.Headers["Location"];
}
How do I avoid the 302 error or how do I account for it wherein I can do a successful form post to simulate the upload

I had a similar case, where I recieved 302 status codes when I expected 200 to be returned (like in Fiddle or Firebug: net tab). I was able to solve the problem by giving an user agent specification to the HttpWebResponse
request.UserAgent = "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:2.0) Gecko/20100101 Firefox/4.0";

Related

login via HttpURLConnection return status code 200 while it should redirect

I tries to login to the website using username and password. when I make a #HttpURLConnection and post it, the status code is 200 but it actually doesn't login. when I checked the login process with Chrome #DevTools Console, I found that after entering the login button, the parameters are sent to the address I used and it returned 302 as a status code. even I add this line to my code by the result doesn't changed.
connection2.setInstanceFollowRedirects(true);
here is my code.
String loginPageURL = "https://AAAAAAAAAA";
CookieManager cookieManager = new CookieManager();
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_ALL);
cookies.forEach(cookie -> cookieManager.getCookieStore().add(null, cookie));
URL url2 = new URL(loginPageURL);
HttpURLConnection connection2 = (HttpURLConnection) url2.openConnection();
connection2.setRequestProperty("Cookie",
StringUtils.join(cookieManager.getCookieStore().getCookies(), ";"));
connection2.setInstanceFollowRedirects(true);
String loginPayload ="mypayload";
connection2.setRequestMethod("POST");
connection2.setDoOutput(true);
connection2.setRequestProperty("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9");
connection2.setRequestProperty("Accept-Encoding", "deflate, br");
connection2.setRequestProperty("Accept-Language", "en-US,en;q=0.9,fa;q=0.8");
connection2.setRequestProperty("Cache-Control", "max-age=0");
connection2.setRequestProperty("Connection", "keep-alive");
connection2.setRequestProperty("Content-Length", String.valueOf(loginPayload.length()));
connection2.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
connection2.setRequestProperty("Host", "https://BBBBBBBBBB");
connection2.setRequestProperty("Origin", "https://BBBBBBBBBB");
connection2.setRequestProperty("Referer", "https://AAAAAAAAAA");
connection2.setRequestProperty("sec-ch-ua", " Not A;Brand;v=99, Chromium;v=100, Google Chrome;v=100");
connection2.setRequestProperty("sec-ch-ua-mobile", "?0");
connection2.setRequestProperty("sec-ch-ua-platform", "Windows");
connection2.setRequestProperty("Sec-Fetch-Dest", "document");
connection2.setRequestProperty("Sec-Fetch-Mode", "navigate");
connection2.setRequestProperty("Sec-Fetch-Site", "same-origin");
connection2.setRequestProperty("Sec-Fetch-User", "?1");
connection2.setRequestProperty("Upgrade-Insecure-Requests", "1");
connection2.setRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36");
DataOutputStream out = new DataOutputStream(connection2.getOutputStream());
out.writeBytes(loginPayload);
System.out.println("login connection status code: "+connection2.getResponseCode());
System.out.println("content length "+loginPayload.length());
out.close();
System.out.println("*************************************************************");
int status = connection2.getResponseCode();
if (status == HttpURLConnection.HTTP_OK) {
String header = connection2.getHeaderField("Location");
System.out.println(header);
}
Anybody can help me figuring out where the problem is?
thanks in advance.

Python beautiful soup and requests submit form data on post url

How can i post form data on the url: http://washington.kdmid.ru/queue-en/Visitor.aspx
When i submit form data with below fields i am getting same page in response instead of redirect to next page.
import requests
from bs4 import BeautifulSoup
location_url = "http://washington.kdmid.ru/queue-en/visitor.aspx"
s = requests.Session()
main_page = s.get(location_url)
main_html = BeautifulSoup(main_page.text)
c_form = main_html.find_all("form")[0]
c_form_submit = c_form.attrs["action"]
data = {e.attrs.get("name"): e.attrs.get("value") for e in c_form.find_all("input")}
data["ctl00$MainContent$txtFam"] = "bsssabassra"
data["ctl00$MainContent$txtIm"] = "Akssssshassya"
data["ctl00$MainContent$txtOt"] = "a"
data["ctl00$MainContent$txtTel"] = "1122334455"
data["ctl00$MainContent$txtEmail"] = "akssbsars2#gmail.com"
data["ctl00$MainContent$DDL_Day"] = 1
data["ctl00$MainContent$DDL_Month"] = 1
data["ctl00$MainContent$TextBox_Year"] = 1993
data["ctl00$MainContent$DDL_Mr"] = "MR"
data["ctl00$MainContent$txtCode"] = captcha_txt
data["ctl00$MainContent$ButtonA"] = "Next"
import json; json.dumps(data)
submit_captcha_resp = s.post("http://washington.kdmid.ru/queue-en/visitor.aspx",
data=json.dumps(data))
final_page = BeautifulSoup(submit_captcha_resp.text)
It wont redirect, because it's not a browser. BS don't run the JS scripts or HTML code. But you get the response.
You should use one of these:
submit_captcha_resp = s.post("yourLongURL", json=data)
or
submit_captcha_resp = s.post("yourLongURL", data=data)
json.dumps() is used to convert a JSON to a string but you don't need that because the webpage which you are posting data uses HTML tag and form tag posts the data without converting it to string. So you shouldn't convert it to a string. You should post it in JSON format.
And as #dharmey said: If you get a 404, you should set a user agent as a popular web browser. For example:
{"User-Agent":"Mozilla/5.0"}
And I think now you have bigger problems like passing the Captcha.
I think you might be posting the data in the wrong way. You could try
submit_captcha_resp = s.post("http://washington.kdmid.ru/queue-en/visitor.aspx",
json=data)
Instead of data=json.dumps(data))
If this dosen't work / the site requires actual form data, try to pass in some headers, as they might be required for the server to recieve the request correctly.
You could just include
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.90 Safari/537.36'
}
submit_captcha_resp = s.post("http://washington.kdmid.ru/queue-en/visitor.aspx",
headers=headers, data=json.dumps(data))
to start out.

Marketing API Export Async Report ads_insights V2.5

I have problems to export Report of ad's statistics since code written in.NET Framework when I use ads_insights (version 2.5). Before when I used reportstats with version 2.3 I could download the report succesfully
My request is //www.facebook.com/ads/ads_insights/export_report?report_run_id=0000000&format=xls&access_token=token
When I execute the request in browser I can download the report succesfully (file xls completed), but when I execute the request since by code .NET Framework (C#) I download the file .xls incomplete [enter image description here][2]
The tasks to get report are (using code .NET C#)
1º request with method POST
graph.facebook.com/v2.5/act_countNumbrer/insights?level=ad&time_range=%7B%27since%27%3A%272015-11-02%27%2C%27until%27%3A%272015-11-02%27%7D&actions_group_by=%5B%27action_type%27%5D&fields=campaign_name%2Cad_name%2Cad_id%2Creach%2Cfrequency%2Cimpressions%2Ccpm%2Ccpp%2Cspend%2Csocial_clicks%2Cunique_clicks%2Cctr%2Cunique_ctr%2Caccount_name%2Cactions%2Ctotal_actions%2Cwebsite_clicks&time_increment=1&access_token=token
Result: successful -> I get a report_run_id
2º request with method GET
graph.facebook.com/v2.5/id_report&access_token=token
Result: successful -> I get a
{
"id": "xxxx",
"account_id": "xxx",
"time_ref": 1447171267,
"time_completed": 1447171269,
"async_status": "Job Completed",
"async_percent_completion": 100,
}
3º when "async_status" is "Job Completed", I execute request
www.facebook.com/ads/ads_insights/export_report?report_run_id=xxxx&format=xls&access_token=token
Result: I download the file .xls incomplete. If you paste the query (URL) in browser you download the report succesful (file xls completed) enter image description here
If I execute the request with code .NET Framework (C#) and saved the response as string the response said we "should update your browser " enter image description here
Why can't I download the report ?
Thank you
Code using to execute the download the report XLS
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;
using System.Xml;
namespace test
{
class Program
{
static void Main(string[] args)
{
string token="token";
string report_run_id="report_number";
string url = "https://www.facebook.com/ads/ads_insights/export_report?report_run_id="+report_run_id+"format=xls&access_token"+token;
//option 1
string reportDownloadUrl = "repo"+DateTime.Now.Ticks + ".xls"; ;
Stream responseStream = null;
try
{
var request = (HttpWebRequest)WebRequest.Create(url);
request.Method = "GET";
//request.UserAgent = "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0)";
var response = (HttpWebResponse)request.GetResponse();
responseStream = response.GetResponseStream(); //relleno el flujo
using (var fileStream = new FileStream(reportDownloadUrl, FileMode.Create, FileAccess.Write))
{
responseStream.CopyTo(fileStream);
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
finally
{
if (responseStream != null) responseStream.Close();
}
Console.WriteLine("File Download" +reportDownloadUrl);
/* //option 2
using (WebClient wc = new WebClient())
{
wc.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
wc.Headers["User-Agent"] = "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0)";
wc.DownloadFile(url,"repo.xls");
}
Console.WriteLine("File Download");
*/
Console.ReadKey();
}
}
}
I had the same issue, trying to download the report using request npm in
nodejs.
Adding the User-Agent header solved my problem.
This works for me. You have some issues in your URL string.
Here is an updated url string:
string url = "https://www.facebook.com/ads/ads_insights/export_report?report_run_id=" + report_id + "&format=csv&access_token=" + accessToken;
This method works.
using (WebClient wc = new WebClient())
{
wc.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
wc.Headers["User-Agent"] = "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0)";
wc.DownloadFile(url, "page1.csv");
}
The report gets saved to:
C:\your\path\to\project\FacebookReportPuller\bin\Debug

Uploading files to Onedrive using REST API

I am trying to upload a file into OneDrive using its REST API. This is what I am trying to accomplish based on documentation available at OneDrive Rest API:
POST https://apis.live.net/v5.0/me/skydrive/files?access_token=ACCESS_TOKEN
Content-Type: multipart/form-data; boundary=A300x
--A300x
Content-Disposition: form-data; name="file"; filename="HelloWorld.txt"
Content-Type: application/octet-stream
Hello, World!
--A300x--
This is what I have:
Uri destination = new Uri(string.Format("https://apis.live.net/v5.0/{0}/files?", folder.ID));
BackgroundUploader uploader = new BackgroundUploader ();
uploader.SetRequestHeader("Authorization", "Bearer " + account.AccessToken);
uploader.SetRequestHeader("Content-Type", "multipart/form-data; boundary=\"foo_bar_baz\"");
List<BackgroundTransferContentPart> parts = new List<BackgroundTransferContentPart>();
BackgroundTransferContentPart metaDataPart = new BackgroundTransferContentPart();
metaDataPart.SetHeader("Content-Disposition", "form-data; name=\"file\";filename=\""+content.Name+"\"");
parts.Add(metaDataPart);
BackgroundTransferContentPart contentPart = new BackgroundTransferContentPart();
contentPart.SetHeader("Content-Type", content.ContentType);
// content is a StorageFile
contentPart.SetFile(content);
response.UploadOperation = await uploader.CreateUploadAsync(destination, parts, "form-data", "foo_bar_baz");
This line below causes an Access violation error and the Windows Store app crashes:
response.UploadOperation = await uploader.CreateUploadAsync(destination, parts, "form-data", "foo_bar_baz");
You are creating two BackgroundTransferContentPart and only adding the fist to your 'List'.
I think you only need one, something like this:
List<BackgroundTransferContentPart> parts = new List<BackgroundTransferContentPart>();
BackgroundTransferContentPart metaDataPart = new BackgroundTransferContentPart();
metaDataPart.SetHeader("Content-Disposition",
"form-data; name=\"file\";filename=\"" + content.Name + "\"");
metaDataPart.SetHeader("Content-Type", content.ContentType);
metaDataPart.SetFile(content);
parts.Add(metaDataPart);
UPDATE: Ok, the above code fixed the Access Violation issue. Why you are getting a 400 error is a mystery.
But another way to upload a file to OneDrive is using the PUT method:
Uri putUri = new Uri(string.Format("https://apis.live.net/v5.0/{0}/files/{1}",
"folder.a4fb14adbccd1917.A4FB14ADBCCD1917!32089",
content.Name));
BackgroundUploader uploader = new BackgroundUploader();
uploader.SetRequestHeader("Authorization", "Bearer " + accessToken);
uploader.Method = "PUT";
UploadOperation putOperation = uploader.CreateUpload(putUri, content);
await putOperation.StartAsync();
Have you tried PUT?

Salesforce rest api INVALID_SESSION_ID

I'm trying to connect my asp.net REST api to salesforce. I'm succesfully going through authentification, but when I start to send POST requests, I'm getting an error
{"errorCode":"INVALID_SESSION_ID","message":"Session expired or invalid"}
Here is my POST request:
//SFServerUrl = "https://na17.salesforce.com/services/";
//url = "data/v28.0/sobjects/Account";
ASCIIEncoding ascii = new ASCIIEncoding();
byte[] postBytes = ascii.GetBytes(postBody);
HttpWebRequest request = WebRequest.Create(Globals.SFServerUrl + url) as HttpWebRequest;
request.Method = "POST";
request.ContentType = "application/json";
request.ContentLength = postBytes.Length;
Stream postStream = request.GetRequestStream();
postStream.Write(postBytes, 0, postBytes.Length);
HttpCookie cookie = HttpContext.Current.Request.Cookies[Globals.SFCookie];
var ticket = FormsAuthentication.Decrypt(cookie.Value);
string authToken = ticket.UserData;
request.Headers.Add("Authorization", "Bearer " + authToken);
postStream.Close();
HttpWebResponse response = request.GetResponse() as HttpWebResponse;
StringBuilder sb = new StringBuilder();
byte[] buf = new byte[8192];
Stream resStream = response.GetResponseStream();
string tempString = null;
int count = 0;
do
{
count = resStream.Read(buf, 0, buf.Length);
if (count != 0)
{
tempString = Encoding.ASCII.GetString(buf, 0, count);
sb.Append(tempString);
}
}
while (count > 0);
return new Tuple<bool, string>(true, sb.ToString());
When I'm trying to send GET request - I recieve 200 response.
Also, I've tried to send a POST Request with the same token from Simple Rest Client and it get's 200 response. I tried to change my "Authorization : Bearer" Header to "Authorization : Oauth", but nothing changed. I also tried to catch this error, get refresh token and send a request again with refreshed token, but nothing changed. Please, help me with this.
Using workbench I was able to POST the following JSON to /services/data/v29.0/sobjects/Account and create a new Account.
{
"Name" : "Express Logistics and Transport"
}
Raw Response
HTTP/1.1 201 Created
Date: Sun, 07 Sep 2014 21:32:06 GMT
Set-Cookie: BrowserId=_HC-bzpTQABC1237vFu2hA;Path=/;Domain=.salesforce.com;Expires=Thu, 06-Nov-2014 21:32:06 GMT
Expires: Thu, 01 Jan 1970 00:00:00 GMT
Sforce-Limit-Info: api-usage=209/15000
Location: /services/data/v29.0/sobjects/Account/0010000000000001AAA
Content-Type: application/json;charset=UTF-8
Content-Encoding: gzip
Transfer-Encoding: chunked
{
"id" : "0010000000000001AAA",
"success" : true,
"errors" : [ ]
}
Things to check:
Your URL. It appears to be missing the leading /services
Is SFServerUrl the same Salesforce pod/server that the Session Id was issued to? If the Session Id came from another pod then it would be invalid on na17.
How did you create the Session Id? If you used OAuth, what scopes did you request?
Is the Session Id coming out of the cookie valid?
Has something else using the same Session Id called logout and invalidated the session?
Incidentally, the Salesforce StackExchange site is a great place to ask Salesforce specific questions.
See also:
Using REST API Resources - Create a Record
The problem was that I added Headers after Content. When I switched these lines of code everything worked.