// $Id: ModifyResult.java,v 1.4 1998/09/10 20:17:20 oliva Exp $

/* Copyright 1998 Alexandre Oliva <oliva@dcc.unicamp.br>
 *
 * This file is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 */

import BR.unicamp.Guarana.*;

/**
 * This example shows how to modify results of Operations.  The
 * MetaObject implemented by this class causes method hashCode of
 * objects it intercepts to always return 0, and causes method
 * toString to have a `modified' word prepended to the original
 * result.
 *
 * @author Alexandre Oliva
 * @version $Revision: 1.4 $
 */
public class ModifyResult extends MetaObject {
    final static java.lang.reflect.Method hashCode, toString;
    static {
	try { hashCode =
		  Object.class.getDeclaredMethod("hashCode", new Class[0]);
	} catch (NoSuchMethodException e) { hashCode = null; }
	try { toString =
		  Object.class.getDeclaredMethod("toString", new Class[0]);
	} catch (NoSuchMethodException e) { toString = null; }
    } 
    public Result handle(final Operation op, final Object ob) {
	final java.lang.reflect.Method meth = op.getMethod();
	if (hashCode.equals(meth))
	    return Result.returnInt(0, op); // make it return 0
	if (toString.equals(meth))
	    return Result.modifyResult; // asks for permission to modify it
	return Result.noResult; // not interested in the result
    }
    public Result handle(final Result res, final Object ob) {
	Operation op = res.getOperation();
	if (toString.equals(op.getMethod()))
	    return Result.returnObject("modified " // replace result
				       + res.getObjectValue(), op);
	return null;
    }
    public static void main(String[ ] argv) {
	Object o = new Object();
	MetaObject[ ] mos = {
	    new MetaLogger().setPrefix("a: "),
	    new ModifyResult(),
	    new MetaLogger().setPrefix("b: ") };
	Guarana.reconfigure(o, null, new SequentialComposer(mos));
	System.out.println(o);
    }
}
