MediawikiConnectionPool.java

From Knot Atlas
Revision as of 10:14, 24 August 2005 by Scott (talk | contribs)
(diff) ← Older revision | Latest revision (diff) | Newer revision → (diff)
Jump to navigationJump to search

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

*/
/*
 * Created on Aug 23, 2005
 */
package wikilink;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Stack;

import org.apache.commons.httpclient.HttpException;
import org.jdom.JDOMException;

/**
 * @author Scott Morrison
 */
public class MediawikiConnectionPool {
	
	String baseURL;
	String username;
	String password;
	int targetSize = 1;
	List activePool = new ArrayList();
	List workingPool = new ArrayList();
	Stack nameStack = new Stack();
	Stack textStack = new Stack();
	Stack descriptionStack = new Stack();
	
	public MediawikiConnectionPool(String baseURL, String username, String password, int size) {
		this.baseURL = baseURL;
		this.username = username;
		this.password = password;
		setPoolSize(size);
	}

	public int setPoolSize(int size) {
		if(size > 0) {
			targetSize = size;
			fillPool();
		}
		return targetSize;
	}
	
	void fillPool() {
		while(activePool.size() + workingPool.size() < targetSize) createConnection();
		while(targetSize < activePool.size()) discardConnection();
	}
	
	void discardConnection() {
		if(!activePool.isEmpty()) activePool.remove(0);
	}
	
	void createConnection() {
		activePool.add(new MediawikiConnection(baseURL, username, password));
	}
	
	public synchronized void scheduleSetPageText(String name, String text, String description) {
		nameStack.push(name);
		textStack.push(text);
		descriptionStack.push(description);
		promptQueue();
	}
	
	synchronized void promptQueue() {
		if(nameStack.isEmpty()) return;
		fillPool();
		if(!connectionAvailable()) {
			return;
		}
		MediawikiConnection conn = getConnection();
		activePool.remove(conn);
		String name = (String)nameStack.pop();
		String text = (String)textStack.pop();
		String description = (String)descriptionStack.pop();
		createThread(conn, name, text, description);
		workingPool.add(conn);
	}
	
	void createThread(final MediawikiConnection conn, final String name, final String text, final String description) {
		new Thread() {
			public void run() {
				try {
					conn.setPageText(name, text, description);
				} catch (IOException e) {
					// who cares?
				} finally {
					workingPool.remove(conn);	
				}
				activePool.add(conn);
				promptQueue();
			}
		}.start();
	}
	
	boolean connectionAvailable() {
		return !activePool.isEmpty();
	}
	
	MediawikiConnection getConnection() {
		if(connectionAvailable()) {
			return (MediawikiConnection)activePool.get(0);
		} else {
			return null;
		}
	}
	
	public static class Test {
		public static void main(String[] args) throws HttpException, IOException, JDOMException {
			MediawikiConnectionPool pool = new MediawikiConnectionPool(
					"http://katlas.math.toronto.edu/w/index.php", "TestRobot", "foobar", 2);
			pool.scheduleSetPageText("foo1", "pool edit "+Math.random(),"");
			pool.scheduleSetPageText("foo2", "pool edit "+Math.random(),"");
			pool.scheduleSetPageText("foo3", "pool edit "+Math.random(),"");
			pool.scheduleSetPageText("foo4", "pool edit "+Math.random(),"");
			pool.scheduleSetPageText("foo5", "pool edit "+Math.random(),"");
			System.out.println("Finished scheduling.");
		}
	}
	
}
/*
<pre>
*/