Wednesday, July 30, 2008

Instrumenting with proxies

Using the InvocationHandler interface one can create a simple, yet sophisticated, means of instrumenting a class to obtain statistics about its usage: 

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.lang.reflect.InvocationTargetException;

public class MyProxy implements InvocationHandler {

    private Object _target;
    public Object getTarget() { return _target; }
    public void setTarget(Object target) { _target = target; }

    public
MyProxy(Object target) {
        _target = target;
    } // constructor

    public Object invoke(Object proxy,
                         Method method,
                         Object[] args)
            throws Throwable {

        Object result = null;

        long start = System.currentTimeMillis();

        try {
            result = method.invoke(_target, args);
        } catch (InvocationTargetException ite) {
            long stop = System.currentTimeMillis();
            // log the exception here

            throw ite.getCause();
        }

        long stop = System.currentTimeMillis();
        // log the invokation results
        // (_target, method, stop - start);

        return result;
    } // invoke()

    public static Object createProxy(Object target) {
        Object result = target;

        Class targetClass = target.getClass();
        result = Proxy.newProxyInstance(
            targetClass.getClassLoader(),
            targetClass.getInterfaces(),
            new
MyProxy(target)
        );


         return result;
    } // createProxy()

} // class MyProxy

Monday, July 28, 2008

limiting characters in an html textarea

Here is a way to limit the amount of text entered into a textarea.  Note, this works in both IE and FireFox.  Also, this only limits characters entered via keystrokes and does not work for copy/paste.

/* -------------------------------------------------------------------------
limits the amount of text that can be typed into a textarea
example usage: <textarea onkeypress="return limitText(event, this, 40);">
--------------------------------------------------------------------------*/
limitText : function(event, textArea, maxChars) {
    var result = true;

    if (textArea.value.length >= maxChars) {

        if (textArea.createTextRange) {
            var range = document.selection.createRange().duplicate();
            result = range.text.length > 0;
        } else {
            result = event.keyCode in { // always let these keys through
                37 : "left",
                39 : "right",
                38 : "up",
                40 : "down",
                33 : "pageUp",
                34 : "pageDown",
                46 : "del",
                36 : "home",
                35 : "end",
                27 : "esc",
                8 : "back"
            };
        }
    }

    return result
} // limitText()