Bypassing Captcha with curl in PHP - php

I am trying to automate the login progress on a captcha protected page. I am using Death By Captcha to translate the image into text and it seems to be working well. I am using curl to load the login page, retrieve the captcha image url, send it to DBC, get the text back and submit a POST request to the login page with the captcha text.
The problem that I'm having is that the captcha image changes when I submit the post request. Since I do not get the same behavior when reloading/or wrongly submitting the form through a browser (I get the same image over and over again), I am assuming that the problem has to do with the cookies or something else that I'm missing that relates to the session.
This is the code that I use to retrieve the data and submit the form:
$ch = curl_init();
// Not sure that I need it, just make sure that the session doesn't change...
curl_setopt($ch, CURLOPT_COOKIESESSION, false);
curl_setopt($ch, CURLOPT_URL, $loginUrl);
// It seems that PHPSESSID cookie parameter might be the parameter that keep the image the same, but it didn't work. I even read it dynamically from the cookie file but it still didn't work
//curl_setopt($ch, CURLOPT_COOKIE, "PHPSESSID=2bp3nhkp3bgftfrr1rjekg03o2");
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookieName);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookieName);
curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1)");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_REFERER, $loginUrl);
$result = curl_exec($ch);
// Resolve the captcha and append it to the post parameters
$captchaText = $this->resolveCaptcha($result);
$postData .= '&LoginForm%5BverifyCode%5D='.$captchaText;
// Resubmit the form with the updated form data
curl_setopt($ch, CURLOPT_REFERER, $loginUrl);
curl_setopt($ch, CURLOPT_URL, $loginUrl);
curl_setopt ($ch, CURLOPT_POST, 1); //FIXED
curl_setopt ($ch, CURLOPT_POSTFIELDS, $postData);
$result = curl_exec($ch);
When I print the end result, I can see that the captcha text was submitted successfully but that the image itself has changed...
I am also attaching a screenshot of the request params as captured with Tamper in a standard Firefox session (so someone might spot if I'm missing something).
The PHP/curl submit code is fully working for non-captcha based sites so the POST parameters submission seems to be working.
It could be that I'm missing something very basic here, any help will be much appreciated.
I also took a look at these posts but couldn't find the answer that I'm looking for.
How CURL Login with Captcha and Session
How to retrieve captcha and save session with PHP cURL?
https://stackoverflow.com/questions/8633282/curl-to-download-a-captcha-and-submit-it

you're using
curl_setopt ($ch, CURLOPT_POST, 0);
in second curl_exec. shoudn't it be
curl_setopt ($ch, CURLOPT_POST, 1);
?

Related

Submitting a form on an external website with cURL is not working

I am trying to retrieve information from an external website using cURL, but the website returns a blank page.
I took a close looker at the network functionality Chrome has and I think I found the problem, but I have no idea how to fix it. As seen in the image below, the server posts to a specific URL and then redirects to another one showing the final result.
This is the code I have right now:
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL,"https://www.politie.nl/aangifte-of-melding-doen/controleer-handelspartij.html?_hn:type=action&_hn:ref=r199_r1_r1_r1");
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS,"url=&query=test");
curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type: application/x-www-form-urlencoded'));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
echo curl_exec ($ch);
curl_close ($ch);
The website is in Dutch, but what I am trying to do is check a certain email, phone number or bank account number to see if they have been involved in any scams, so I would like to have the information that a user gets after submitting the form on the website.
The form is on this website: https://www.politie.nl/aangifte-of-melding-doen/controleer-handelspartij.html
I hope someone can help me and thank you for your time.
As was pointed out in one of the comments to your question, a redirect occurs after the form is submitted. But not only that - information transfer between the form submit request and the request after redirect happens through a session, with session id stored in a cookie, so in order to get the results you have to enable cookies, too.
// follow redirects
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
// store and send cookies
$tmpfname = dirname(__FILE__).'/cookie.txt';
curl_setopt($ch, CURLOPT_COOKIEJAR, $tmpfname);
curl_setopt($ch, CURLOPT_COOKIEFILE, $tmpfname);

Curl with POST method gives "HTTP Status 405" while the submit form is a POST. Input doesn't get prefilled from paired URL parameter

I searched around google for a similar problem but couldn't find any, or couldn't formulate my question precisely enough, so I come to you.
I'm trying to login to forclosure.com from my localhost using Curl.
If you go to forclosure.com/login, you'll find that the login form uses a POST method, whereas when I try to login with Curl, it gives me an HTTP Status 405 error.
I tried to use Curl with a GET request instead and it passes (while the form is a POST..).
But now comes another problem, the password input isn't recognized in the URL and the login doesn't pass.
For exemple, if you try those parameters :
https://www.foreclosure.com/login?key=testkey&password=testpass
You will see that the username "key" gets filled, but not the password "password".
Same thing seems to happen with the search bar above with the name "q"
Thank you in advance. If the solution seems obvious to you, bear in mind that I'm still learning and would like to be pointed towards the right path.
Thanks to CBroe, I decided to try and use CURLOPT_URL with /login.html instead of just /login.. and not surprisingly, it works.
But I had to use GET parameters with CURLOPT_POST on true.
Here's the code for the interested:
//-----------------------------------Login Part
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://www.foreclosure.com/login.html?key='.$loginInfo['key'].'&password='.$loginInfo['password'];
curl_setopt($ch, CURLOPT_POST, 1); //Wouldn't work without it
curl_setopt($ch, CURLOPT_USERAGENT, $userAgent);
curl_setopt($ch, CURLOPT_COOKIEFILE, NULL); //NULL to use cookies in memory, use $cookiefile to store them in disk
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_NOBODY, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 0);
curl_setopt($ch, CURLOPT_BINARYTRANSFER, 1);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
curl_exec($ch);
curl_close($ch);

cURL Login - Not working with # in email input

I'm trying to use cURL to login to a website, but it doesn't seem to be working. I started by testing it on my own site which works, but when I try on the site that I actually need it wont login, and just gets the login page.
$loginUrl = 'https://www.ekomi.co.uk/login.php';
$postData = 'login_email=-----&login_passwort=-----';
$ch = curl_init();
$agent = $_SERVER['HTTP_USER_AGENT'];
curl_setopt($ch, CURLOPT_USERAGENT, $agent);
curl_setopt($ch, CURLOPT_URL, $loginUrl);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postData);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_COOKIEJAR, 'cookies/cookies.txt');
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookies/cookies.txt');
$postResult = curl_exec($ch);
print_r($postResult);
It does give an error that $_SERVER index is undefined, but it still allowed me to login to my site, also I am assuming that the $postData should be the names of the user and password fields.
Is there anything wrong with the script that could be the problem, or could it maybe be the way which the site logs in?
Edit
The problem seems to be because of the # symbol in the login email, I've tried putting %40 as suggested in other questions but this doesn't work.
First thing you must navigate to the page and get the csrf (Cross-site request forgery-basically it checks that the login form is seen by the user, sets a random hash in the session and checks if you give it back) and then make the post.

Logging in to a webpage through CURL, differently

There's a webpage that I need to log in to. I used CURL with post to login, but it's not enough. When you log in from the website the post also includes a string that is always changing. Is threre a way to get over that?
I use this:
$ch = curl_init();
curl_setopt ($ch, CURLOPT_URL, $url);
curl_setopt ($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (Windows; U; Windows NT 5.1; he-IL; rv:1.8.1.6) Gecko/20070725 Firefox/2.0.0.6");
curl_setopt ($ch, CURLOPT_REFERER, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);
curl_setopt($ch, CURLOPT_POST, TRUE);
$post = "username=$username&password=$password";
curl_setopt($ch, CURLOPT_POSTFIELDS, $post);
$result = curl_exec($ch);
$info = curl_getinfo($ch);
curl_close($ch);
It's like I need the code to actually go to the webpage and fill the form regularly.
I looked everywhere but all I could find was using post data.
Thanks!
To pass that you need to visit the page with the form, grab the field and then use it in POST request when you submit the form.
I suggest you visit the form page not only for that, but also for the following reasons (some of which can be used to figure people using automatic requests):
You recieve cookies
You don't fake referrer, you actually visited the page
You might want to check form fields to see if there's any new ones added since you wrote the script. That could be the case if form setup changes and you might want to adapt to that, if you don't then your script might stop working one day

Using curl with PHP to authenticate - mysterious security

I'm trying to make a script that would run through some sites that I visit every day and get the most interesting info/statistics from them. I wanted to use curl for this purpose, because some of these sites require authentification. Everything was ok until I bumped into the site: rossnet.pl which seems to be somehow secured 'cause I can't authenticate myself at all.
The form that I want to use can be found here:
https://www.rossnet.pl/rossnetlogin.aspx
On the left, under the text: "Mam konto w Rossnet.pl - Logowanie". It doesn't seem to have any hidden input fields, only two text fields for credentials, called:
- "dnn$ctr1203$ViewLogin$txtUserLogin"
- "dnn$ctr1203$ViewLogin$txtUserPass"
I'm using the code shown below but the page returned by the server seems as if exactly nothing happened (no error messages, it seems to look the same as when I don't send any POST data).
Does anyone have a clue about what may be wrong? In the code below I put in actual account credentials for you to be able to test the script if you wish to help me.
Here you can see how does the script below work on my server:
http://kremuwa.netii.net/rossman/skrypt.php
<?php
$url = "https://www.rossnet.pl/rossnetlogin.aspx";
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_COOKIEJAR, 'cookie.txt');
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookie.txt');
curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (X11; U; Linux x86_64; en-US; rv:1.9.2.13) Gecko/20101206 Ubuntu/10.10 (maverick) Firefox/3.6.13');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_HEADER, 1);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_REFERER, $url);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, 'dnn$ctr1203$ViewLogin$txtUserLogin=warzywko3000&dnn$ctr1203$ViewLogin$txtUserPass=password123');
$output = curl_exec($ch);
curl_close($ch);
echo $output;
?>
Login forms are sometimes protected with challenges that prevent you from directly submitting the form without loading the page first. I've listed a few options that could stand in your way.
One option is cookie challenges, it's also the easiest to deal with by just loading the page (fetch the cookie) and send it along with the form submission.
Another option is a hidden field challenge; a hidden form field is populated with a challenge code and the submission expects that value to be sent as well.
The last option I can think of is an even more difficult approach involving JavaScript; the page would use JavaScript to load the challenge string, maybe obfuscate it a bit and then send it along (via hidden form field or ajax request).

Categories