Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to login to wordpress programmatically?

I need to perform some action in wordpress admin panel programmatically but can't manage how to login to Wordpress using C# and HttpWebRequest.

Here is what I do:

private void button1_Click(object sender, EventArgs e)
        {
            string url = "http://localhost/wordpress/wp-login.php";
            HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
            CookieContainer cookies = new CookieContainer();

            SetupRequest(url, request, cookies);
            //request.Accept = "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8";
            //request.Headers["Accept-Language"] = "uk,ru;q=0.8,en-us;q=0.5,en;q=0.3";
            //request.Headers["Accept-Encoding"] = "gzip,deflate";
            //request.Headers["Accept-Charset"] = "windows-1251,utf-8;q=0.7,*;q=0.7";


            string user = "test";
            string pwd = "test";

            request.Credentials = new NetworkCredential(user, pwd);

            string data = string.Format(
                "log={0}&pwd={1}&wp-submit={2}&testcookie=1&redirect_to={3}",
                user, pwd, 
                System.Web.HttpUtility.UrlEncode("Log In"),
                System.Web.HttpUtility.UrlEncode("http://localhost/wordpress/wp-admin/"));

            SetRequestData(request, data);

            ShowResponse(request);
}

private static void SetupRequest(string url, HttpWebRequest request, CookieContainer cookies)
        {
            request.CookieContainer = cookies;
            request.UserAgent = "Mozilla/5.0 (Windows; U; Windows NT 6.0; uk; rv:1.9.1.2) Gecko/20090729 Firefox/3.5.2 (.NET CLR 3.5.30729)";
            request.KeepAlive = true;
            request.Timeout = 120000;
            request.Method = "POST";
            request.Referer = url;
            request.ContentType = "application/x-www-form-urlencoded";
        }

        private void ShowResponse(HttpWebRequest request)
        {
            HttpWebResponse response = (HttpWebResponse)request.GetResponse();
            responseTextBox.Text = (((HttpWebResponse)response).StatusDescription);
            responseTextBox.Text += "\r\n";
            StreamReader reader = new StreamReader(response.GetResponseStream());
            responseTextBox.Text += reader.ReadToEnd();
        }

        private static void SetRequestData(HttpWebRequest request, string data)
        {
            byte[] streamData = Encoding.ASCII.GetBytes(data);
            request.ContentLength = streamData.Length;

            Stream dataStream = request.GetRequestStream();
            dataStream.Write(streamData, 0, streamData.Length);
            dataStream.Close();
        }

But unfortunately in responce I get only HTML source code of login page and it seems that cookies don't contain session ID. All requests which I perform after that code also return HTML source of login page so I can assume that it does not login correctly.

Can anybody help me to solve that problem or give working example?


Main thing which I want to achieve is scanning for new images in Nextgen Gallery plugin for Wordpress. Is there XML-RPC way of doing that?

Thanks in advance.

like image 962
T-Rex Avatar asked Aug 15 '09 19:08

T-Rex


3 Answers

Since WordPress implement a redirect, leaving the page (redirecting) prevents the webrequest from getting the proper cookie.

in order to get the relevant cookie, one must prevent redirects.

request.AllowAutoRedirect = false;

than use the cookie-conatainer for login.

see the following code: (based on an example from Albahari's C# book)

        string loginUri = "http://www.someaddress.com/wp-login.php";
        string username = "username";
        string password = "pass";
        string reqString = "log=" + username + "&pwd=" + password;
        byte[] requestData = Encoding.UTF8.GetBytes(reqString);

        CookieContainer cc = new CookieContainer();
        var request = (HttpWebRequest)WebRequest.Create(loginUri);
        request.Proxy = null;
        request.AllowAutoRedirect = false;
        request.CookieContainer = cc;
        request.Method = "post";

        request.ContentType = "application/x-www-form-urlencoded";
        request.ContentLength = requestData.Length;
        using (Stream s = request.GetRequestStream())
            s.Write(requestData, 0, requestData.Length);

        using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
        {
            foreach (Cookie c in response.Cookies)
                Console.WriteLine(c.Name + " = " + c.Value);
        }

        string newloginUri = "http://www.someaddress.com/private/";
        HttpWebRequest newrequest = (HttpWebRequest)WebRequest.Create(newloginUri);
        newrequest.Proxy = null;
        newrequest.CookieContainer = cc;
        using (HttpWebResponse newresponse = (HttpWebResponse)newrequest.GetResponse())
        using (Stream resSteam = newresponse.GetResponseStream())
        using (StreamReader sr = new StreamReader(resSteam))
            File.WriteAllText("private.html", sr.ReadToEnd());
        System.Diagnostics.Process.Start("private.html");
like image 69
TomerBu Avatar answered Sep 25 '22 22:09

TomerBu


I don't know if others will find this helpful, but I just used the WordPress API to log in. I created a user (CRON_USR) who "logs in" at night as part of a cron job and does some tasks. The code is this:

require(dirname(__FILE__) . '/wp-load.php' );
$user = wp_authenticate(CRON_USR, CRON_PWD);
wp_set_auth_cookie($user->ID, true, $secure_cookie); //$secure_cookie is an empty string
do_action('wp_login', CRON_USR);
wp_redirect('http://www.mysite.com/wp-admin/');
like image 44
Kungfug Avatar answered Sep 22 '22 22:09

Kungfug


Thanks to everyone. I managed how to make it work only when using sockets. Wordpress sends several Set-Cookie headers but HttpWebRequest handles only one instance of such header so some cookies are lost. When using sockets I can get all needed cookies and login to admin panel.

like image 27
T-Rex Avatar answered Sep 24 '22 22:09

T-Rex