MediawikiConnection.java: Difference between revisions

From Knot Atlas
Jump to navigationJump to search
mNo edit summary
mNo edit summary
Line 1: Line 1:
/*
/*
This page contains the source code for MediawikiConnection.java, the java component of Scott Morrison's [[WikiLink` package]].
This page contains the source code for MediawikiConnection.java, the java component of Scott Morrison's [[WikiLink` package]]. See also [[MediawikiConnectionPool.java]].


<pre>
<pre>

Revision as of 09:13, 24 August 2005

/* This page contains the source code for MediawikiConnection.java, the java component of Scott Morrison's WikiLink` package. See also MediawikiConnectionPool.java.

*/
package wikilink;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;

import org.apache.commons.httpclient.DefaultHttpMethodRetryHandler;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpException;
import org.apache.commons.httpclient.NameValuePair;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.methods.multipart.FilePart;
import org.apache.commons.httpclient.methods.multipart.MultipartRequestEntity;
import org.apache.commons.httpclient.methods.multipart.Part;
import org.apache.commons.httpclient.methods.multipart.StringPart;
import org.apache.commons.httpclient.params.HttpMethodParams;
import org.jdom.Document;
import org.jdom.Element;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;

/**
 * @author Scott Morrison
 */
public class MediawikiConnection {
	
	private String baseURL;
	private HttpClient client = new HttpClient();
	
	public MediawikiConnection(String baseURL) {
		this.baseURL = baseURL;
	}
	
	public MediawikiConnection(String baseURL, String username, String password) {
		this.baseURL = baseURL;
		doLogin(username, password);
	}
	
	private boolean doLogin(String username, String password) {
		PostMethod post = new PostMethod(baseURL + "?title=Special:Userlogin&action=submit");
		// post.getParams().setCookiePolicy(CookiePolicy.BROWSER_COMPATIBILITY);
		
		// enable automatic retrying
		post.getParams().setParameter(HttpMethodParams.RETRY_HANDLER, 
	    		new DefaultHttpMethodRetryHandler(3, false));
		
		NameValuePair[] data = {
			new NameValuePair("wpName", username),
		    new NameValuePair("wpPassword", password),
		    new NameValuePair("wpRemember", "1"),
		    // ugh... this changed between 1.4beta5 and 1.4.7
		    // for 1.4beta5
		    new NameValuePair("wpLoginAttempt", "1"),
		    // for 1.4.7
		    new NameValuePair("wpLoginattempt", "Log in")
		};
		
		post.setRequestBody(data);
		
		int status;
		try {
			status = client.executeMethod(post);
		} catch (HttpException e) {
			return false;
		} catch (IOException e) {
			return false;
		} finally {
			post.releaseConnection();
		}
		return (status == 302);
	}

	public String getPageText(String title) throws HttpException, IOException, JDOMException {
		String URL = baseURL + "?title=Special:Export/" + title;
		GetMethod get = new GetMethod(URL);
		
		// enable automatic retrying
		get.getParams().setParameter(HttpMethodParams.RETRY_HANDLER, 
	    		new DefaultHttpMethodRetryHandler(3, false));
		
		client.executeMethod(get);
		InputStream is = get.getResponseBodyAsStream();
		
		SAXBuilder builder = new SAXBuilder();
		Document doc = builder.build(is);
		Element page = doc.getRootElement().getChild("page");
		String text = "";
		if(page != null)
			text = page.getChild("revision").getChild("text").getText();

		// finally, make sure we release the connection!
		get.releaseConnection();
		
		return text;
	}
	
	public void setPageTextAsync(String title, String text) throws IOException {
		setPageTextAsync(title, text, "");		
	}
	
	public boolean setPageText(String title, String text) throws IOException {
		return setPageText(title, text, "");		
	}

	public void setPageTextAsync(final String title, final String text, final String summary) throws IOException {
		new Thread() {
			public void run() {
				try {
					setPageText(title, text, summary);
				} catch (IOException e) {
					// hehe... who cares? No one's listening anyway.
				}
			}
		}.start();
	}
		
	public boolean setPageText(String title, String text, String summary) throws IOException {
		String URL = baseURL + "?title=" + title + "&action=edit";
		
		// first, load the edit page, to get an 'edittime' and 'edittoken'
		String editTime = "";
		String editToken = "";
		GetMethod get = new GetMethod(URL);
		// enable automatic retrying
		get.getParams().setParameter(HttpMethodParams.RETRY_HANDLER, 
	    		new DefaultHttpMethodRetryHandler(3, false));
		client.executeMethod(get);
		
		// now sift through the response looking for the editime and edittoken
		String response = get.getResponseBodyAsString();
		get.releaseConnection();
		java.util.regex.Pattern regex1 = java.util.regex.Pattern.compile(
				"value=\"([0-9]+)\" name=\"wpEdittime\"");
		java.util.regex.Matcher matcher1 = regex1.matcher(response);
		if(matcher1.find()) editTime = matcher1.group(1);

		java.util.regex.Pattern regex2 = java.util.regex.Pattern.compile(
			"value=\"([0-9a-z]+)\" name=\"wpEditToken\"");
		java.util.regex.Matcher matcher2 = regex2.matcher(response);
		if(matcher2.find()) editToken = matcher2.group(1);		
		
		PostMethod post = new PostMethod(URL);
		
		NameValuePair[] data = {
			new NameValuePair("wpTextbox1", text),
			new NameValuePair("wpEdittime", editTime),
			new NameValuePair("wpEditToken", editToken),			
		    new NameValuePair("wpSummary", summary)
		};
			
		post.setRequestBody(data);
		
		int status;
		try {
			status = client.executeMethod(post);
			System.out.println("Finished setPageText post, status: " + status);			
			System.out.println(post.getResponseBodyAsString());
		} catch (HttpException e) {
			return false;
		} catch (IOException e) {
			return false;
		} finally {
			post.releaseConnection();
		}
	
		return (status == 302);
	}
	
	public boolean uploadFile(String filename, String description) throws IOException {
		return uploadFile(new File(filename), description);
	}
	
	public boolean uploadFile(File f, String description) throws IOException {
		String URL = baseURL + "?title=Special:Upload";
		
		PostMethod upload = new PostMethod(URL);
		Part[] parts = {
				new StringPart("wpUploadDescription", description),
				new StringPart("wpUploadAffirm", "1"),
				new StringPart("wpIgnoreWarning", "1"),
				new StringPart("wpUpload", "Upload file"),
				new FilePart("wpUploadFile", f.getName(), f)
		};
		upload.setRequestEntity( new MultipartRequestEntity(parts, upload.getParams()) );

		int status;
		try {
			status = client.executeMethod(upload);
		} catch (HttpException e) {
			return false;
		} catch (IOException e) {
			return false;
		} finally {
			upload.releaseConnection();
		}
	
		return (status == 302);
	}	
	
	// deleteFile doesn't work! The mediawiki software says that something is wrong with the login session.
	public boolean deleteFile(String filename, String reason) throws HttpException, IOException {
		String URL1 = baseURL + "?title=Image:" + filename + "&action=delete";
				
		// first, load the edit page, to get an 'edittime' and 'edittoken'
		String editTime = "";
		String editToken = "";
		GetMethod get = new GetMethod(URL1);
		// enable automatic retrying
		get.getParams().setParameter(HttpMethodParams.RETRY_HANDLER, 
	    		new DefaultHttpMethodRetryHandler(3, false));
		client.executeMethod(get);
		
		// now sift through the response looking for the editime and edittoken
		String response = get.getResponseBodyAsString();
		get.releaseConnection();
		java.util.regex.Pattern regex1 = java.util.regex.Pattern.compile(
				"value=\"([0-9]+)\" name=\"wpEdittime\"");
		java.util.regex.Matcher matcher1 = regex1.matcher(response);
		if(matcher1.find()) editTime = matcher1.group(1);

		java.util.regex.Pattern regex2 = java.util.regex.Pattern.compile(
			"value=\"([0-9a-z]+)\" name=\"wpEditToken\"");
		java.util.regex.Matcher matcher2 = regex2.matcher(response);
		if(matcher2.find()) editToken = matcher2.group(1);		
		
		String URL2 = baseURL + "?title=Image:" + filename + "&action=delete" + "&image=" + filename;		
		PostMethod post = new PostMethod(URL2);
		// post.getParams().setCookiePolicy(CookiePolicy.BROWSER_COMPATIBILITY);
		
		NameValuePair[] data = {
			new NameValuePair("wpConfirm", "1"),
			// new NameValuePair("wpEdittime", editTime),			
		    new NameValuePair("wpReason", reason),
		    new NameValuePair("wpConfirmB", "Confirm"),
			new NameValuePair("wpEditToken", editToken)
		};
			
		post.setRequestBody(data);
		
		int status;
		try {
			status = client.executeMethod(post);
		} catch (HttpException e) {
			return false;
		} catch (IOException e) {
			return false;
		} finally {
			post.releaseConnection();
		}
		
		return (status == 302);
	}
		
	public static class Test {
		public static void main(String[] args) throws HttpException, IOException, JDOMException {
			MediawikiConnection conn1 = new MediawikiConnection(
					"http://katlas.math.toronto.edu/w/index.php", "TestRobot", "foobar");
			MediawikiConnection conn2 = new MediawikiConnection(
					"http://katlas.math.toronto.edu/w/index.php", "TestRobot", "foobar");
			MediawikiConnection conn3 = new MediawikiConnection(
					"http://katlas.math.toronto.edu/w/index.php", "TestRobot", "foobar");
//			MediawikiConnection conn2 = new MediawikiConnection(
//					"http://math.berkeley.edu/~scott/w/index.php", "TestRobot", "foobar");
//			MediawikiConnection conn3 = new MediawikiConnection(
//					"http://katlas.math.toronto.edu/w/index.php", "ScottSysopRobot", "******");
//			System.out.println(conn.getPageText("Main_Page"));
//			System.out.println(conn.setPageText("foo", "crel3", "auto!"));
			conn1.setPageTextAsync("foo","async1! "+Math.random());
			conn1.setPageTextAsync("foo","async2! "+Math.random());
			conn1.setPageTextAsync("foo","async3! "+Math.random());
//			System.out.println(conn.deleteFile("K7a4_m.gif","redundant, see [[Image:K7a4.gif]]"));
		}
	}
}
/*
  • /