0

I have been puzzling for a while over how to login to the website: https://steamcommunity.com/login/home/?goto=market%2F using a perl script however after writing a program using WWW::Mechanize:

my $login = "https://steamcommunity.com/login/home/?goto=market%2F";
my $username = "USR";
my $password = "PASS";
my $mech = WWW::Mechanize->new();
$mech->cookie_jar(HTTP::Cookies->new());
$mech->get($login);
$mech->form_name('loginForm');
$mech->field(login => $username);
$mech->field(passwd => $password);
$mech->click();

I have found out that Mechanize does not support javascript websites, at this point I'm stumped, any help or suggestions would be really appreciated :).

Thanks in advance for your time.

Seb Morris

1 Answers1

0

By default Mechanize doesn't support JS, but there are things like JavaScript::SpiderMonkey and WWW::Mechanize::PluginJavascript.

However, I think, it would be easier just find that JS on the web site and mimic its behavior by plain vanilla Mechanize.

In your case DoLogin JS is not that complex, so you can continue building your Mechanize logic based on that. From https://steamcommunity.com/public/javascript/login.js?v=264288658&

function DoLogin()
{
var form = document.forms['logon'];

var username = form.elements['username'].value;
username = username.replace( /[^\x00-\x7F]/g, '' ); // remove non-standard-ASCII characters

var password = form.elements['password'].value;
password = password.replace( /[^\x00-\x7F]/g, '' ); // remove non-standard-ASCII characters

if ( g_bLoginInFlight || password.length == 0 || username.length == 0 )
    return;

g_bLoginInFlight = true;
$('login_btn_signin').hide();
$('login_btn_wait').show();

new Ajax.Request( 'https://steamcommunity.com/login/getrsakey/',
    {
        method: 'post',
        parameters: {
            username: username,
            donotcache: ( new Date().getTime() )
        },
        onSuccess: OnRSAKeyResponse,
        onException: function( req, e ) { throw e; }
    }
);
}

Edit: here is the code for the RSA key function

function OnRSAKeyResponse( transport )
{
var results = transport.responseJSON;
if ( results.publickey_mod && results.publickey_exp && results.timestamp )
{
    var form = document.forms['logon'];

    var pubKey = RSA.getPublicKey( results.publickey_mod, results.publickey_exp );
    var username = form.elements['username'].value;
    username = username.replace( /[^\x00-\x7F]/g, '' ); // remove non-standard-ASCII characters
    var password = form.elements['password'].value;
    password = password.replace( /[^\x00-\x7F]/g, '' ); // remove non-standard-ASCII characters
    var encryptedPassword = RSA.encrypt( password, pubKey );
    new Ajax.Request( 'https://steamcommunity.com/login/dologin/',
        {
            method: 'post',
            parameters: {
                password: encryptedPassword,
                username: username,
                emailauth: form.elements['emailauth'].value,
                loginfriendlyname: form.elements['loginfriendlyname'].value,
                                    captchagid: form.elements['captchagid'].value,
                captcha_text: form.elements['captcha_text'].value,
                emailsteamid: form.elements['emailsteamid'].value,
                rsatimestamp: results.timestamp,
                remember_login: ( form.elements['remember_login'] && form.elements['remember_login'].checked ) ? 'true' : 'false',
                donotcache: ( new Date().getTime() )
            },
            onSuccess: OnLoginResponse,
            onException: function( req, e ) { throw e; }
        }
    );
} 
awksp
  • 11,764
  • 4
  • 37
  • 44
Oleg Gryb
  • 5,122
  • 1
  • 28
  • 40
  • Do you know how i should implement that into my code as it is not perl? – user3648548 May 18 '14 at 17:02
  • I can describe a high level plan only, but you'll need to understand JS logic well. At the first step you'll need to use something like LWP::UserAgent to get a public RSA key from the server by posting to URL in Ajax. Then you'll need to encrypt a password and make a second call as provided in OnRSAKeyResponse function. There are RSA encryption functions available in Perl. If all of that seem too complex for you, then you'll probably need to start playing with JS plugins mentioned above. I was able to Mechanize Login to TDAmeritrade, but it required some efforts: sf.net/projects/stock-pager – Oleg Gryb May 19 '14 at 00:12
  • Thanks alot for the reply, any chance you could direct me towards the right reading material? Or show me what you mean? Thanks alot for your time in replying. – user3648548 May 19 '14 at 15:13